Các thành phần tập tin zip có được xây dựng vào XE2 sẽ làm điều này.
Có phương thức quá tải Open
nhận được thông số đầu vào TStream
.
Để trích xuất các tệp riêng lẻ, bạn có thể gọi phương thức quá tải Read
chuyển tên của tệp mà bạn muốn trích xuất. Tệp được giải nén được trả về dưới dạng phiên bản mới của TStream
. Bạn có thể sử dụng CopyFrom
trên trường hợp đó để chuyển tệp được trích xuất sang luồng của bạn.
var
ZipFile: TZipFile;
DownloadedStream, DecompressionStream, MyStream: TStream;
LocalHeader: TZipHeader;
...
ZipFile := TZipFile.Create;
try
ZipFile.Open(DownloadedStream, zmRead);
ZipFile.Read('myzippedfile', DecompressionStream, LocalHeader);
try
MyStream.CopyFrom(DecompressionStream, DecompressionStream.Size);
finally
DecompressionStream.Free;
end;
finally
ZipFile.Free;
end;
Lưu ý rằng tôi đã không kiểm tra mã này, tôi vừa viết mã này dựa trên mã nguồn cho TZipFile
và tài liệu chứa trong mã nguồn đó. Có thể có một vài nếp nhăn trong điều này nhưng nếu mã hoạt động như quảng cáo, nó đáp ứng nhu cầu của bạn một cách hoàn hảo.
OK, bây giờ tôi đã thử nghiệm vì tôi tò mò. Đây là chương trình cho thấy rằng tất cả điều này hoạt động như được quảng cáo:
program ZipTest;
{$APPTYPE CONSOLE}
uses
System.SysUtils,
System.Classes,
System.Zip;
procedure ExtractToFile(
const ZipFileName: string;
const ZippedFileIndex: Integer;
const ExtractedFileName: string
);
var
ZipFile: TZipFile;
DownloadedStream, DecompressionStream, OutputStream: TStream;
LocalHeader: TZipHeader;
begin
DownloadedStream := TFileStream.Create(ZipFileName, fmOpenRead);
try
ZipFile := TZipFile.Create;
try
ZipFile.Open(DownloadedStream, zmRead);
ZipFile.Read(ZippedFileIndex, DecompressionStream, LocalHeader);
try
OutputStream := TFileStream.Create(ExtractedFileName, fmCreate);
try
OutputStream.CopyFrom(DecompressionStream, DecompressionStream.Size);
finally
OutputStream.Free;
end;
finally
DecompressionStream.Free;
end;
finally
ZipFile.Free;
end;
finally
DownloadedStream.Free;
end;
end;
begin
try
ExtractToFile('C:\desktop\test.zip', 0, 'C:\desktop\out.txt');
except
on E: Exception do
Writeln(E.ClassName, ': ', E.Message);
end;
end.
Lưu ý rằng tôi trích xuất theo chỉ mục thay vì tên tệp vì điều đó thuận tiện hơn cho tôi. Và tôi đã sử dụng luồng tệp thay vì luồng bộ nhớ mà tôi tưởng tượng bạn sẽ sử dụng. Tuy nhiên, vì phương thức TZipFile
hoạt động với TStream
Tôi chắc chắn rằng mã sẽ hoạt động với các luồng của bất kỳ biểu mẫu nào.
Đây là câu hỏi mới nhất trong loạt câu hỏi về tệp ZIP. Tôi biết rằng bạn đang sử dụng XE2 và tôi tự hỏi tại sao bạn dường như miễn cưỡng sử dụng được xây dựng trong lớp ZIP mà XE2 cung cấp. Tôi đã không thấy bất cứ điều gì để chỉ ra rằng nó sẽ không đáp ứng yêu cầu của bạn. Trong thực tế, chính xác là khả năng này làm việc trực tiếp với các luồng khiến tôi cảm thấy nó có đủ tính tổng quát cho bất kỳ ứng dụng nào.
Cảm ơn rất nhiều David !!! – maxfax
Tôi không thấy phương thức Đọc (tôi đã kiểm tra nhanh), có thông tin thuần túy về nó http://docwiki.embarcadero.com/VCL/en/System.Zip.TZipFile.Đọc – maxfax
@maxfax Bạn có phiên bản Delphi nào? Tôi đã có Pro và đi kèm với nguồn. Câu trả lời của tôi cho cả hai câu hỏi ZIP gần đây của bạn dựa hoàn toàn vào việc đọc nguồn. Tôi biết chính xác không có gì về các tập tin ZIP và không có gì về thành phần này. Nếu bạn có mã nguồn thì đó sẽ là một trợ giúp lớn cho bạn tôi nghĩ. –