我正在将应用程序从 delphi 2007 迁移到 delphi xe,但在读取 ascii 文件并将内容存储在字符串中的过程中遇到问题。
此代码在 Delphi 2007 中有效
function LoadFileToStr(const FileName: TFileName): String;
var
FileStream : TFileStream;
begin
FileStream:= TFileStream.Create(FileName, fmOpenRead or fmShareDenyWrite);
try
if FileStream.Size>0 then
begin
SetLength(Result, FileStream.Size);
FileStream.Read(Pointer(Result)^, FileStream.Size);
end;
finally
FileStream.Free;
end;
end;
但是当我在 Delphi XE 中执行这段代码时,结果只是像“?????????”这样的符号。我知道 Delphi XE 是 unicode 所以我改变了这些行
SetLength(Result, FileStream.Size);
FileStream.Read(Pointer(Result)^, FileStream.Size);
到
SetLength(Result, FileStream.Size*2);
FileStream.Read(Pointer(Result)^, FileStream.Size);
将文件内容存储在unicode字符串中,但结果是相同的。
如何修复此过程以读取该文件的内容?
您的代码不起作用,因为您正在使用 unicode 字符串作为缓冲区读取文件的内容,因此您只是将字节从 TFileStream 的内部缓冲区移动到 unicode 字符串,忽略编码。
您可以轻松修复您的程序,只需将结果类型更改为
AnsiString
function LoadFileToStr(const FileName: TFileName): AnsiString;
TFile.ReadAllText
函数,而不是在一行代码中读取文件的内容并处理文件的编码。
您可以使用 ReadAllText 函数通过一行代码来实现这一点。像这样:
Uses IOUtils;
TFile.ReadAllText(FileName);
或
TFile.ReadAllText(FileName, s, TEncoding.ASCII) // if you want to force ASCII (other) encoding
它将正确检测 ANSI、Unicode 和二进制文件。
您应该考虑编码,例如:
function LoadFileToStr(const FileName: TFileName): String;
var
FileStream : TFileStream;
Bytes: TBytes;
begin
Result:= '';
FileStream:= TFileStream.Create(FileName, fmOpenRead or fmShareDenyWrite);
try
if FileStream.Size>0 then begin
SetLength(Bytes, FileStream.Size);
FileStream.Read(Bytes[0], FileStream.Size);
end;
Result:= TEncoding.ASCII.GetString(Bytes);
finally
FileStream.Free;
end;
end;
//test
procedure TForm2.Button1Click(Sender: TObject);
begin
ShowMessage(LoadFileToStr('C:\autoexec.bat'));
end;
我建议使用TStringList来加载文件的内容,然后将结果设置为variable.Text,例如:
function LoadFileToStr(const FileName: TFileName): String;
var LStrings: TStringList;
begin
LStrings := TStringList.Create;
try
LStrings.Loadfromfile(FileName);
Result := LStrings.text;
finally
FreeAndNil(LStrings);
end;
end;
这样你就不用担心任何事情,恕我直言,它将向后和未来兼容。
编辑:如果您需要从 TStream 后代加载,请将 LoadFromFile 替换为 LoadFromStream。