65.9K
CodeProject 正在变化。 阅读更多。
Home

使用 java.util.zip 类写入 zip 文件时的一个 Bug

starIconstarIconstarIconstarIcon
emptyStarIcon
starIcon

4.58/5 (15投票s)

2004 年 5 月 9 日

CPOL

2分钟阅读

viewsIcon

139813

描述了使用 java.util.zip 类将二进制文件写入 zip 文件时出现的问题

引言

我正在用 C# 编写一个小型的 .NET 应用程序,并寻找一个可以让我读取和写入 zip 文件的库。这时,我的第一次 Google 搜索给了我一个链接到 使用 J# 类库中的 Zip 类来压缩文件和数据 (C#)。太棒了! - 这是我最初的反应,但并没有持续多久。你可以读取 zip 文件,但是当你写入 zip 文件时,如果你有二进制文件(正如你通常会遇到的情况),生成的 zip 文件将会损坏,你无法将其读回。有趣的是,WinZip 可以打开它(忽略头部错误),而一位微软人员在 MS 新闻组中提出的建议是使用 WinZip 提取所有文件,然后重新压缩。 哈哈。如果他们可以选择将 WinZip 纳入其中,为什么还要使用压缩库呢?

甚至没有关于这个 bug 的 KB 文章 - 太糟糕了!我使用这些类时浪费了大约半天的时间,因为我最初认为问题出在我的代码中。无论如何,这是一个警告。如果你使用的是 BCL 1.1 版本,请不要使用 J# 类库进行压缩/解压缩Heath Stewart (C# MVP 和 CodeProject 编辑) 告诉我 BCL 2.0 包含压缩功能 - 这真是个好消息。而且在发布之前,一个非常好的 J# 类库的免费替代品是 SharpZipLib,我强烈推荐它。

Bug 演示

  1. 创建一个新的 C# 控制台应用程序项目
  2. 添加对 vjslib 的引用(...Microsoft.NET\Framework\v1.1.4322\vjslib.dll)
  3. 将以下代码复制/粘贴到你的主 cs 文件中 :-
    using System;
    using System.IO;
    using java.util.zip;
    
    class MainClass
    {
      [STAThread]
      static void Main(string[] args)
      {
        BugDemo();
      }
    
      static void BugDemo()
      {
        //Write zip file
        ZipOutputStream os = new ZipOutputStream(
          new java.io.FileOutputStream("test.zip"));
        ZipEntry ze = new ZipEntry("gluk.gif");
        ze.setMethod(ZipEntry.DEFLATED);
        os.putNextEntry(ze);
        java.io.FileInputStream fs = 
          new java.io.FileInputStream("gluk.gif");
        sbyte[] buff = new sbyte[1024];
        int n = 0;
    
        while ((n=fs.read(buff,0,buff.Length))>0)
        {
          os.write(buff,0,n);
        }
        fs.close();
        os.closeEntry();      
        os.close();
    
        Console.WriteLine("Okay, the zip has been written.");
    
        //Read zip file
        try
        {
          //Bug will occur here
          ZipFile zf = new ZipFile("test.zip");  
        }
        catch
        {
          Console.WriteLine("Bug confirmed!");
        }
      }
    }
  4. 现在确保在与可执行文件相同的文件夹中有一个 gluk.gif 文件。

  5. 编译并运行。

解决方法

这个问题没有真正的解决方法。你可以使用我上面提到的替代库,或者等待 Whidbey 的发布。

© . All rights reserved.