admin 管理员组

文章数量: 1184232

工具类ZipUtils 如下:

packagecom.hai.tang.util;importjava.io.BufferedOutputStream;importjava.io.ByteArrayOutputStream;importjava.io.File;importjava.io.FileInputStream;importjava.io.FileOutputStream;importjava.io.IOException;importjava.io.InputStream;importjava.util.List;importjava.util.Map;importjava.util.zip.ZipEntry;importjava.util.zip.ZipInputStream;importjava.util.zip.ZipOutputStream;publicclassZipUtils{/**
     * 文件夹压缩成ZIP
     *
     * @param srcDir           待压缩文件夹路径
     * @param zipPathName      压缩文件输出路径(含名称及后缀)
     * @param keepDirStructure 是否保留原来的目录结构:
     *                         true:保留文件目录结构;
     *                         false:不保留文件目录结构,把所有文件一起压缩,即提取文件夹及其所有子文件夹里的文件进行压缩,压缩后的压缩包里不含有文件夹
     *                         (注意:不保留文件目录结构可能会出现同名文件,会压缩失败。例如:子文件夹 a下有 a.txt,子文件夹 b下有 a.txt )
     * @throws RuntimeException 压缩失败会抛出运行时异常
     */publicstaticvoidtoZip(String srcDir,String zipPathName,boolean keepDirStructure){try(FileOutputStream fileOutputStream =newFileOutputStream(newFile(zipPathName));BufferedOutputStream out =newBufferedOutputStream(fileOutputStream);ZipOutputStream zos =newZipOutputStream(out);){File sourceFile =newFile(srcDir);compress(sourceFile, zos, sourceFile.getName(), keepDirStructure);}catch(Exception e){thrownewRuntimeException("压缩错误", e);}}/**
     * 多文件压缩成ZIP
     *
     * @param imageMap    需要压缩的文件列表,键值对为 <文件名,文件的字节数组>,文件名必须包含后缀
     * @param zipPathName 压缩文件输出路径(含名称及后缀)
     * @throws RuntimeException 压缩失败会抛出运行时异常
     */publicstaticvoidtoZip(Map<String,byte[]> imageMap,String zipPathName)throwsRuntimeException{try(FileOutputStream fileOutputStream =newFileOutputStream(newFile(zipPathName));BufferedOutputStream out =newBufferedOutputStream(fileOutputStream);ZipOutputStream zos =newZipOutputStream(out);){for(Map.Entry<String,byte[]> map : imageMap.entrySet()){
                zos.putNextEntry(newZipEntry(map.getKey()));
                zos.write(map.getValue());
                zos.closeEntry();}}catch(Exception e){thrownewRuntimeException("压缩错误", e);}}/**
     * 多文件压缩成ZIP
     *
     * @param srcFiles    需要压缩的文件列表
     * @param zipPathName 压缩文件输出路径(含名称及后缀)
     * @throws RuntimeException 压缩失败会抛出运行时异常
     */publicstaticvoidtoZip(List<File> srcFiles,String zipPathName)throwsRuntimeException{try(FileOutputStream fileOutputStream =newFileOutputStream(newFile(zipPathName));BufferedOutputStream out =newBufferedOutputStream(fileOutputStream);ZipOutputStream zos =newZipOutputStream(out);){for(File srcFile : srcFiles){byte[] buf =newbyte[2048];
                zos.putNextEntry(newZipEntry(srcFile.getName()));int len;FileInputStream in =newFileInputStream(srcFile);while((len = in.read(buf))!=-1){
                    zos.write(buf,0, len);}
                zos.closeEntry();}}catch(Exception e){thrownewRuntimeException("压缩错误", e);}}/**
     * 递归压缩方法
     *
     * @param sourceFile       源文件
     * @param zos              zip输出流
     * @param name             压缩后的名称
     * @param keepDirStructure 是否保留原来的目录结构:
     *                         true:保留目录结构;
     *                         false:不保留文件目录结构,把所有文件一起压缩,即提取文件夹及其所有子文件夹里的文件进行压缩,压缩后的压缩包里不含有文件夹
     *                         (注意:不保留文件目录结构可能会出现同名文件,会压缩失败。例如:子文件夹 a下有 a.txt,子文件夹 b下有 a.txt )
     */privatestaticvoidcompress(File sourceFile,ZipOutputStream zos,String name,boolean keepDirStructure){byte[] buf =newbyte[2048];try{if(sourceFile.isFile()){// 向zip输出流中添加一个zip实体,构造器中name为zip实体的文件的名字
                zos.putNextEntry(newZipEntry(name));// copy文件到zip输出流中int len;FileInputStream in =newFileInputStream(sourceFile);while((len = in.read(buf))!=-1){
                    zos.write(buf,0, len);}
                zos.closeEntry();
                in.close();}else{File[] listFiles = sourceFile.listFiles();if(listFiles ==null|| listFiles.length ==0){// 需要保留原来的文件结构时,需要对空文件夹进行处理if(keepDirStructure){// 空文件夹的处理
                        zos.putNextEntry(newZipEntry(name +"/"));// 没有文件,不需要文件的copy
                        zos.closeEntry();}}else{for(File file : listFiles){// 判断是否需要保留原来的文件结构if(keepDirStructure){// 注意:file.getName()前面需要带上父文件夹的名字加一斜杠,// 不然最后压缩包中就不能保留原来的文件结构,即:所有文件都跑到压缩包根目录下了compress(file, zos, name +"/"+ file.getName(), keepDirStructure);}else{compress(file, zos, file.getName(), keepDirStructure);}}}}}catch(Exception e){thrownewRuntimeException("压缩错误", e);}}/**
     * zip格式的压缩文件解压
     *
     * @param zipFilePath 待解压的压缩文件
     * @param destDir     要解压到的文件夹
     */publicstaticvoidunzip(String zipFilePath,String destDir){try(FileInputStream fis =newFileInputStream(zipFilePath);ZipInputStream zis =newZipInputStream(fis);){File destDirFile =newFile(destDir);if(!destDirFile.exists()){
                destDirFile.mkdirs();// 确保目标目录存在}ZipEntry ze = zis.getNextEntry();byte[] buffer =newbyte[1024];int length;while(ze !=null){File newFile =newFile(destDir +File.separator + ze.getName());// 确保文件所在的目录存在
                newFile.getParentFile().mkdirs();FileOutputStream fos =newFileOutputStream(newFile);while((length = zis.read(buffer))>0){
                    fos.write(buffer,0, length);}
                fos.close();
                zis.closeEntry();
                ze = zis.getNextEntry();}}catch(IOException e){
            e.printStackTrace();}}/**
     * InputStream 或 FileInputStream 转 byte[ ]
     *
     */publicstaticbyte[]toByteArray(InputStream input){int nRead;byte[] data =newbyte[16384];try(ByteArrayOutputStream buffer =newByteArrayOutputStream()){while((nRead = input.read(data,0, data.length))!=-1){
                buffer.write(data,0, nRead);}
            buffer.flush();return buffer.toByteArray();}catch(IOException e){
            e.printStackTrace();}returnnewbyte[1];}}

测试:

1.压缩文件夹:

importcom.hai.tang.util.ZipUtils;publicclassTest{publicstaticvoidmain(String[] args){//将 zipTest 文件夹压缩到 C:\myCode\zipTestOut\zipTest.zipZipUtils.toZip("C:\\myCode\\zipTest","C:\\myCode\\zipTestOut\\zipTest.zip",true);}}

2 .选择多个文件压缩:

importcom.hai.tang.util.ZipUtils;importjava.io.File;importjava.util.ArrayList;importjava.util.List;publicclassTest{publicstaticvoidmain(String[] args){//要压缩的文件列表List<File> fileList =newArrayList<>();
        fileList.add(newFile("C:\\myCode\\zipTest\\sql表字段逗号拼接临时文件.txt"));
        fileList.add(newFile("C:\\myCode\\zipTest\\pom.xml"));//开始压缩到C:\myCode\zipTestOut\zipList.zipZipUtils.toZip(fileList,"C:\\myCode\\zipTestOut\\zipList.zip");}}

3.对 zip 格式解压缩:

importcom.hai.tang.util.ZipUtils;publicclassTest{publicstaticvoidmain(String[] args){//将 Myfolder.zip 压缩包解压到 C:\myCode\zipTestOut 下ZipUtils.unzip("C:\\myCode\\zipTestOut\\zipList.zip","C:\\myCode\\zipTestOut");}}

4.有时候我们可能只有文件流或者文件的字节数组,可通过字文件节数组压缩:

importcom.hai.tang.util.ZipUtils;importjava.io.FileInputStream;importjava.io.*;importjava.util.HashMap;importjava.util.Map;publicclassTest{publicstaticvoidmain(String[] args)throwsFileNotFoundException{FileInputStream inputStream1 =newFileInputStream("C:\\myCode\\zipTest\\aa.jpg");FileInputStream inputStream2 =newFileInputStream("C:\\myCode\\zipTest\\sql表字段逗号拼接临时文件.txt");FileInputStream inputStream3 =newFileInputStream("C:\\myCode\\zipTest\\kone-rbac-2.3.2.6.jar");//将上面三个文件的输入流转为字节数组byte[] bytes1 =ZipUtils.toByteArray(inputStream1);byte[] bytes2 =ZipUtils.toByteArray(inputStream2);byte[] bytes3 =ZipUtils.toByteArray(inputStream3);//三个文件字节数组存入mapMap<String,byte[]> map =newHashMap<>();
        map.put("aa.jpg", bytes1);
        map.put("sql表字段逗号拼接临时文件.txt", bytes2);
        map.put("kone-rbac-2.3.2.6.jar", bytes3);//将 上面三个文件 压缩到 C:\myCode\MyzipTest.zipZipUtils.toZip(map,"C:\\myCode\\zipTestOut\\MyzipTest.zip");}}

参考:

本文标签: 不保留文 件目录结 压缩文件