Как получить Delphi 2006 TStringList.LoadFromFile для загрузки файлов UTF-16
У меня есть приложение Delphi 2006, в которое я добавляю код для обработки некоторых сгенерированных файлов данных CSV. TStringList.LoadFromFile дал странные результаты, и я только что разработал файлы в кодировке UTF-16.
Обновление до XE планируется, но на данный момент не вариант.
Какой самый простой путь для обработки этих файлов с D2006? Я предполагаю, что они могут быть сопоставлены с 8-битным ASCII без каких-либо проблем - они являются "чистыми" CSV - только цифры и запятые и т. Д., И я не думаю, что будут какие-либо проблемы с символами, которых нет в 8 набор
2 ответа
TStringList
не поддерживает UTF-16 в D2006, поэтому вам придется загружать и декодировать данные файла вручную, прежде чем помещать вывод в ваш TStringList
, Например:
var
sl: TStringList;
{$IFNDEF D2009_OR_LATER}
ms: TMemoryStream;
ptr: PWideChar;
s: AnsiString;
dlen, slen: Integer;
{$ENDIF}
begin
...
{$IFDEF D2009_OR_LATER}
sl.LoadFromFile('...', TEncoding.Unicode);
{$ELSE}
ms := TMemoryStream.Create;
try
ms.LoadFromFile('...');
ptr := PWideChar(ms.Memory);
dlen := ms.Size div SizeOf(WideChar);
if (dlen >= 1) and (PWord(ptr)^ = $FEFF) then
begin
Inc(ptr);
Dec(dlen);
end;
slen := WideCharToMultiByte(0, 0, ptr, dlen, nil, 0, nil, nil);
if slen > 0 then begin
SetLength(s, slen);
WideCharToMultiByte(0, 0, ptr, dlen, PAnsiChar(s), slen, nil, nil));
end;
sl.Text := s;
finally
ms.Free;
end;
{$ENDIF}
...
end;
На случай, если существует риск потери данных, вы можете попробовать использовать JCL TJclWideStringList.