下面是我的函数,它接受一个压缩文件,并通过一次读取1024个字符将其转换为txt文件。
procedure DecompressFile(const ACompressedFile, ADestinationFile : String);
var
SourceStream : TFileStream;
DestinationStream : TFileStream;
DecompressionStream : TDecompressionStream;
nRead : Integer;
Buffer: array [0..1023] of Char;
begin
SourceStream := TFileStream.Create(ACompressedFile, fmOpenRead);
try
DestinationStream := TFileStream.Create(ADestinationFile, fmCreate);
try
DecompressionStream := TDecompressionStream.Create(SourceStream);
try
repeat
nRead := DecompressionStream.Read(Buffer, 1024);
DestinationStream.Write(Buffer, nRead);
until nRead = 0;
finally
DecompressionStream.Free;
end;
finally
DestinationStream.Free;
end;
finally
SourceStream.Free;
end;
end;
我的问题是,在Delphi7的情况下,这会产生正确的txt文件,但在DelphiXE4的情况下会在每个字符之间引入垃圾值。
示例:
Delphi 7: abcdedfgh
Delphi XE4: aNULbNULcNULdNULeNULfNULgNULhNUL
NUL插入每个字符之间。我尝试更改申报
Buffer: array [0..1023] of Char;
到CCD_ 1,但这不起作用。
首先让我们假设解压缩流类,无论它是什么,都是正确实现的。在这种情况下,问题中的代码实际上是好的。它成功地解压缩了文件。尽管如此,它还是有点草率,因为它分配的缓冲区是您使用的缓冲区的两倍大。缓冲区应该是一个字节数组,而不是字符数组。使用SizeOf(Buffer),而不是重复那个神奇的1024常量。Write调用最好是WriteBuffer来添加错误检查。
两个输出之间的区别很简单,一个用8位编码编码,另一个用16位编码,可能是UTF-16。
很难说这是否是故意的。需要查看创建压缩文件的过程。例如,压缩文件可能是通过压缩Delphi字符串创建的。在D7中,该字符串是8位编码的,但在DXE4中,它是16位编码的。
一个明显的步骤是比较两个输入文件,D7和DXE4文件。你期望它们完全相同。但是他们是吗?
另一个可能的原因是您的解压缩流类已损坏。它看起来像众所周知的ZLib类。
此校正应解决D7和DXE4:之间的差异
Buffer: array [0..1023] of **Ansi**Char;
但在操作内存时,最好避免使用可能会对编码产生不利影响的字符。。。最好使用字节
Buffer: array [0..1023] of **Byte**;
然后,如果没有缓冲区,它会更好:
DestinationStream.CopyFrom(DecompressionStream , DecompressionStream.Size);