压缩文件,首先FileInputStream从源文件读取数据,再通过ZipOutputStream写入目标文件。当压缩文件的过程中,目标文件名通过ZipEntry(String name)设置。
Java.util.zip.ZipOutputStream类处理文件压缩时,若文件名是中文,会出现乱码。可导入apache-ant包中的org.apache.tools.zop.ZipOutputStream类,再设置编码可解决文件名乱码问题。
先来个简单的实例:
package com.whpcrs.util;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import org.apache.tools.zip.ZipEntry;
import org.apache.tools.zip.ZipOutputStream;
public class SimpleZip {
public static final int BUFFER_SIZE = 1024;
public static void main(String[] args) throws IOException {
String src = "d:\\测试.txt";
String des = "d:\\测试.zip";
ZipOutputStream out = null;
try{
out = new ZipOutputStream(new FileOutputStream(des));
out.setEncoding("GBK"); //设置编码,否则文件名还是乱码
File srcFile = new File(src);
singleFileZip(srcFile, out);
}catch(Exception e){
e.printStackTrace();
}finally{
if(out != null){
out.close();
}
}
}
public static void singleFileZip(File srcFile, ZipOutputStream out) throws IOException {
FileInputStream in = null;
try{
ZipEntry entry = new ZipEntry(srcFile.getName());
out.putNextEntry(entry); //设置目标压缩文件的文件名(zip条目),一般使用源文件的文件名
in = new FileInputStream(srcFile);
byte[] buffer = new byte[BUFFER_SIZE];
int c = 0;
while((c = in.read(buffer, 0, buffer.length)) != -1){
out.write(buffer, 0, c);
}
}catch(Exception e){
e.printStackTrace();
}finally{
in.close();
}
}
别忘了ZipOutputStream和ZipEntry是apache-ant包里的,下为结果截图:
接下来是一个压缩文件/文件夹的例子,直接看源码吧。
public static void main(String[] args) throws IOException {
String src = "d:\\测试文件夹";
String des = "d:\\测试.zip";
ZipOutputStream out = null;
try {
out = new ZipOutputStream(new FileOutputStream(des));
out.setEncoding("GBK"); // 设置编码,否则文件名还是乱码
File srcFile = new File(src);
String base = srcFile.getName();
fileZip(srcFile, out, base);
} catch (Exception e) {
e.printStackTrace();
} finally {
if (out != null) {
out.close();
}
}
}
/**
*
* @param srcFile
* @param out
* @param base 目标文件的文件名(包括路径,也称为zip条目)
* @throws IOException
*/
public static void fileZip(File srcFile, ZipOutputStream out, String base)
throws IOException {
if (!srcFile.exists()) {
System.out.println("Not Found File: " + srcFile.getPath());
return;
}
if (srcFile.isFile()) {
out.putNextEntry(new ZipEntry(base));
FileInputStream in = null;
in = new FileInputStream(srcFile);
byte[] buffer = new byte[1024];
int c = 0;
while ((c = in.read(buffer, 0, buffer.length)) != -1) {
out.write(buffer, 0, c);
}
in.close();
} else {
if (srcFile.isDirectory()) {
base = base + File.separator;
File[] subFiles = srcFile.listFiles();
for (File subFile : subFiles) {
fileZip(subFile, out, base + subFile.getName());
}
}
}
}
下为结果截图,可以看到源文件夹"d:\\测试文件夹"整个都在zip中清楚的显示。
接下来,稍作修改,得到一个可以处理多个源文件的压缩方法。
public static void filesZip(String[] srcs, String des) throws IOException{
ZipOutputStream out = null;
try {
out = new ZipOutputStream(new FileOutputStream(des));
out.setEncoding("GBK");
for(String file : srcs){
File srcFile = new File(file);
String base = srcFile.getName();
fileZip(srcFile, out, base);
}
} catch (Exception e) {
e.printStackTrace();
} finally {
if (out != null) {
out.close();
}
}
}