使用org.apache.tools.zip解压和压缩文件

这篇博客介绍了在Android中解压zip文件时遇到的中文乱码问题及其解决方案。由于Windows和Mac系统压缩文件时使用的编码不同,导致解压时可能出现乱码。文章提出使用Apache的org.apache.tools.zip包,它可以支持GBK编码,从而正确处理中文文件名。提供了具体的解压缩代码示例,包括使用ZipFile和ZipOutputStream设置编码为GBK,以避免乱码。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

解压zip文件中文乱码

参考博客:

Android中解压zip中文乱码处理

android通过org.apache.tools.zip解压zip压缩文件,支持中文名

关于为什么解压zip包时会出现中文乱码,可以参考博客Android中解压zip中文乱码处理,主要原因就是不同的操作系统压缩文件时采用的编码方式不同, windows默认是GBK编码方式, mac系统默认的文字编码格式是utf-8。

解决方案: 由于java自带的解压缩包不能在压缩文件中存在中文名,使用apache的开发包org.apache.tools.zip可以支持中文。我们可以直接引用该包,但是Apache的包相对于Android说有点偏大不适合于Android环境,所以我们可以找到解压缩的那部分代码进行改造即可。此处自己直接引用该包。

apache-ant-zip.jar包可以自行搜索下载, 将此jar包复制到工程的libs目录下,在代码头部需要导入下面的包:

import org.apache.tools.zip.ZipEntry;
import org.apache.tools.zip.ZipFile;

解压缩的相关代码参考博客android通过org.apache.tools.zip解压zip压缩文件,支持中文名, 相关代码如下:


	/**
	 * 使用 org.apache.tools.zip.ZipFile 解压文件,它与 java 类库中的 java.util.zip.ZipFile
	 * 使用方式是一新的,只不过多了设置编码方式的 接口。
	 *
	 * 注,apache 没有提供 ZipInputStream 类,所以只能使用它提供的ZipFile 来读取压缩文件。
	 *
	 * @param archive 压缩包路径
	 * @param decompressDir  解压路径
	 * @throws IOException
	 * @throws FileNotFoundException
	 * @throws ZipException
	 */
	public static void readByApacheZipFile(String archive, String decompressDir)
			throws IOException, FileNotFoundException, ZipException {
		BufferedInputStream bi;
		ZipFile zf = new ZipFile(archive, "GBK");// 支持中文

		Enumeration e = zf.getEntries();
		while (e.hasMoreElements()) {
			ZipEntry ze2 = (ZipEntry) e.nextElement();
			String entryName = ze2.getName();
			String path = decompressDir + "/" + entryName;
			if (ze2.isDirectory()) {
				Log.d("readByApacheZipFile", "正在创建解压目录 - " + entryName);
				File decompressDirFile = new File(path);
				if (!decompressDirFile.exists()) {
					decompressDirFile.mkdirs();
				}
			} else {
				Log.d("readByApacheZipFile", "正在创建解压文件 - " + entryName);
				String fileDir = path.substring(0, path.lastIndexOf("/"));
				File fileDirFile = new File(fileDir);
				if (!fileDirFile.exists()) {
					fileDirFile.mkdirs();
				}
				BufferedOutputStream bos = new BufferedOutputStream(
						new FileOutputStream(decompressDir + "/" + entryName));
				bi = new BufferedInputStream(zf.getInputStream(ze2));
				byte[] readContent = new byte[1024];
				int readCount = bi.read(readContent);
				while (readCount != -1) {
					bos.write(readContent, 0, readCount);
					readCount = bi.read(readContent);
				}
				bos.close();
			}
		}
		zf.close();
	}

压缩相关代码

 ZipOutputStream out = new ZipOutputStream(new FileOutputStream(outputFileName));
 out.setEncoding("GBK");


//调用压缩的方法
zip(out, new File(inputFileName), "");

private void zip(ZipOutputStream out, File f, String base)
            throws Exception {

        if (f.isDirectory()) {// 文件夹
            File[] fl = f.listFiles();
            out.putNextEntry(new ZipEntry(base + "/"));
            base = base.length() == 0 ? "" : base + "/";
            for (int i = 0; i < fl.length; i++) {
                System.out.println("i=" + i + "," + fl[i].getName());
                zip(out, fl[i], base + fl[i].getName());
            }
        } else {// 文件
            if (base.length() == 0) {// 当base为空时,表示是压缩指定的一个文件,否则就是压缩文件夹下的所有文件
                base = f.getName();
            }
            out.putNextEntry(new ZipEntry(base));
            FileInputStream in = new FileInputStream(f);
            int b;
            byte[] buffer = new byte[1024];// 提高文件压缩的速度
            while ((b = in.read(buffer)) != -1) {
                out.write(buffer, 0, b);
            }
            in.close();
        }

}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值