在Windows中创建Zip文件并在Linux中提取Zip文件

时间:2010-03-31 01:02:12

标签: java

我在Windows下创建了一个zip文件(连同目录),如下所示(代码从http://www.exampledepot.com/egs/java.util.zip/CreateZip.html中选取):

package sandbox;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;

/**
 *
 * @author yan-cheng.cheok
 */
public class Main {

    /**
     * @param args the command line arguments
     */
    public static void main(String[] args) {
        // These are the files to include in the ZIP file
        String[] filenames = new String[]{"MyDirectory" + File.separator + "MyFile.txt"};

        // Create a buffer for reading the files
        byte[] buf = new byte[1024];

        try {
            // Create the ZIP file
            String outFilename = "outfile.zip";
            ZipOutputStream out = new ZipOutputStream(new FileOutputStream(outFilename));

            // Compress the files
            for (int i=0; i<filenames.length; i++) {
                FileInputStream in = new FileInputStream(filenames[i]);

                // Add ZIP entry to output stream.
                out.putNextEntry(new ZipEntry(filenames[i]));

                // Transfer bytes from the file to the ZIP file
                int len;
                while ((len = in.read(buf)) > 0) {
                    out.write(buf, 0, len);
                }

                // Complete the entry
                out.closeEntry();
                in.close();
            }

            // Complete the ZIP file
            out.close();
        } catch (IOException e) {
            e.printStackTrace();
        }

    }

}

使用http://www.exampledepot.com/egs/java.util.zip/GetZip.html

,可以在Windows下无问题地提取新创建的zip文件

但是,我意识到如果我使用http://www.exampledepot.com/egs/java.util.zip/GetZip.html的修改版本在Linux下提取新创建的zip文件。原始版本不使用zipEntry.isDirectory())检查目录。

public static boolean extractZipFile(File zipFilePath, boolean overwrite) {
    InputStream inputStream = null;
    ZipInputStream zipInputStream = null;
    boolean status = true;

    try {
        inputStream = new FileInputStream(zipFilePath);

        zipInputStream = new ZipInputStream(inputStream);
        final byte[] data = new byte[1024];

        while (true) {
            ZipEntry zipEntry = null;
            FileOutputStream outputStream = null;

            try {
                zipEntry = zipInputStream.getNextEntry();

                if (zipEntry == null) break;

                final String destination = Utils.getUserDataDirectory() + zipEntry.getName();

                if (overwrite == false) {
                    if (Utils.isFileOrDirectoryExist(destination)) continue;
                }

                if (zipEntry.isDirectory())
                {
                    Utils.createCompleteDirectoryHierarchyIfDoesNotExist(destination);
                }
                else
                {
                    final File file = new File(destination);
                    // Ensure directory is there before we write the file.
                    Utils.createCompleteDirectoryHierarchyIfDoesNotExist(file.getParentFile());

                    int size = zipInputStream.read(data);

                    if (size > 0) {
                        outputStream = new FileOutputStream(destination);

                        do {
                            outputStream.write(data, 0, size);
                            size = zipInputStream.read(data);
                        } while(size >= 0);
                    }
                }
            }
            catch (IOException exp) {
                log.error(null, exp);
                status = false;
                break;
            }
            finally {
                if (outputStream != null) {
                    try {
                        outputStream.close();
                    }
                    catch (IOException exp) {
                        log.error(null, exp);
                        break;
                    }
                }

                if (zipInputStream != null) {
                    try {
                        zipInputStream.closeEntry();
                    }
                    catch (IOException exp) {
                        log.error(null, exp);
                        break;
                    }
                }
            }

        }   // while(true)
    }
    catch (IOException exp) {
        log.error(null, exp);
        status = false;
    }
    finally {
        if (zipInputStream != null) {
            try {
                zipInputStream.close();
            } catch (IOException ex) {
                log.error(null, ex);
            }
        }

        if (inputStream != null) {
            try {
                inputStream.close();
            } catch (IOException ex) {
                log.error(null, ex);
            }
        }
    }
    return status;
}

“MyDirectory \ MyFile.txt”而非MyFile.txt放在MyDirectory文件夹下。

我尝试通过将zip文件创建代码更改为

来解决问题
    String[] filenames = new String[]{"MyDirectory" + "/" + "MyFile.txt"};

但是,这是一个合格的解决方案,通过对分隔符进行硬编码吗?它会在Mac OS下运行吗? (我没有Mac试试)

1 个答案:

答案 0 :(得分:2)

是的,你的解决方案(虽然显然不优雅)是正确的方法。 “/”应该在zipentry中使用,而不是本地的File.separator