Java实现将文件夹下的文件压缩成压缩包,复制文件(文件夹)到指定目录

2023-01-02 00:00:00 文件 文件夹 压缩包

Java将文件压缩成压缩包

关于java下载文件的时候, 多是把很多文件压缩成压缩包之后在下载, 之前在网上查了一些资料, 将文件压缩成压缩包, 里面还有复制文件或文件夹的方法,最近又使用到这个, 所以记录一下, 方便后续可能再次使用到。

代码片.

import java.io.*;
import java.util.zip.ZipEntry;
import java.util.zip.ZipOutputStream;

/** * 将文件夹下面的文件 * 打包成zip压缩文件 * */
public final class FileToZip { 

    static int count = 0;

    private FileToZip(){ }

    /** * 将存放在sourceFilePath目录下的源文件,打包成fileName名称的zip文件,并存放到zipFilePath路径下 * @param sourceFilePath :待压缩的文件路径 * @param zipFilePath :压缩后存放路径 * @param fileName :压缩后文件的名称 * @return */
    public static boolean fileToZip(String sourceFilePath, String zipFilePath, 
    String fileName){ 
        boolean flag = false;
        File sourceFile = new File(sourceFilePath);
        FileInputStream fis = null;
        BufferedInputStream bis = null;
        FileOutputStream fos = null;
        ZipOutputStream zos = null;

        if(sourceFile.exists() == false){ 
            System.out.println("待压缩的文件目录:"+sourceFilePath+"不存在.");
        }else{ 
            try { 
                File zipFile = new File(zipFilePath + "/" + fileName +".zip");
                if(zipFile.exists()){ 
                    System.out.println(zipFilePath + "目录下存在名字为:" + fileName +".zip" +"打包文件.");
                }else{ 
                    File[] sourceFiles = sourceFile.listFiles();
                    if(null == sourceFiles || sourceFiles.length<1){ 
                        System.out.println("待压缩的文件目录:" + sourceFilePath + "里面不存在文件,无需压缩.");
                    }else{ 
                        fos = new FileOutputStream(zipFile);
                        zos = new ZipOutputStream(new BufferedOutputStream(fos));
                        byte[] bufs = new byte[1024*10];
                        for(int i=0;i<sourceFiles.length;i++){ 
                            //创建ZIP实体,并添加进压缩包
                            ZipEntry zipEntry = new ZipEntry(sourceFiles[i].getName());
                            zos.putNextEntry(zipEntry);
                            //读取待压缩的文件并写进压缩包里
                            fis = new FileInputStream(sourceFiles[i]);
                            bis = new BufferedInputStream(fis, 1024*10);
                            int read = 0;
                            while((read=bis.read(bufs, 0, 1024*10)) != -1){ 
                                zos.write(bufs,0,read);
                            }
                            bis.close();
                            fis.close();
                        }
                        flag = true;
                    }
                }
            } catch (FileNotFoundException e) { 
                e.printStackTrace();
                throw new RuntimeException(e);
            } catch (IOException e) { 
                e.printStackTrace();
                throw new RuntimeException(e);
            } finally{ 
                //关闭流
                try { 
                    if(null != bis) bis.close();
                    if(null != zos) zos.close();
                    if(null != fis) fis.close();
                    if(null != fos) fos.close();
                } catch (IOException e) { 
                    e.printStackTrace();
                    throw new RuntimeException(e);
                }
            }
        }
        return flag;
    }
    /** * 压缩成ZIP * @param srcDir 压缩文件夹路径 * @param out 压缩文件输出流 * @param KeepDirStructure 是否保留原来的目录结构,true:保留目录结构; * false:所有文件跑到压缩包根目录下(注意:不保留目录结构可能会出现同名文件,会压缩失败) * @throws RuntimeException 压缩失败会抛出运行时异常 */
    public static void toZip(String srcDir, OutputStream out, 
    boolean KeepDirStructure) throws RuntimeException { 
        long start = System.currentTimeMillis();
        ZipOutputStream zos = null ;
        try { 
            zos = new ZipOutputStream(out);
            File sourceFile = new File(srcDir);
            compress(sourceFile,zos,sourceFile.getName(),KeepDirStructure);
            long end = System.currentTimeMillis();
            System.out.println("压缩完成,耗时:" + (end - start) +" ms");
        } catch (Exception e) { 
            throw new RuntimeException("zip error from ZipUtils",e);
        }finally{ 
            if(zos != null){ 
                try { 
                    zos.close();
                } catch (IOException e) { 
                    e.printStackTrace();
                }
            }
        }
    }

	private static void compress(File sourceFile, ZipOutputStream zos, String name, boolean KeepDirStructure) throws Exception{ 
        byte[] buf = new byte[BUFFER_SIZE];    		
        if(sourceFile.isFile()){ 
            // 向zip输出流中添加一个zip实体,构造器中name为zip实体的文件的名字
            zos.putNextEntry(new ZipEntry(name));
            // copy文件到zip输出流中
            int len;
            FileInputStream in = new FileInputStream(sourceFile);
            while ((len = in.read(buf)) != -1){ 
                zos.write(buf, 0, len);
            }
            // Complete the entry
            zos.closeEntry();
            in.close();
        } else { 
            File[] listFiles = sourceFile.listFiles();
            if(listFiles == null || listFiles.length == 0){ 
                // 需要保留原来的文件结构时,需要对空文件夹进行处理
                if(KeepDirStructure){ 
                    // 空文件夹的处理
                    zos.putNextEntry(new ZipEntry(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);
                    }
                }
            }
        }
    }

    /** * 将压缩包删除 * @param file 压缩包文件 */
    public static boolean delDirectory(File file) { 
    	if (file.isDirectory()) { 
    		File[] files = file.listFiles();
    		for (File item : files) { 
				delDirectory(item);
			}
    	}
    	return file.delete();
    }

    private static final int  BUFFER_SIZE = 2 * 1024;

	/** * 复制文件(文件夹) 复制文件路径需要到文件名.后缀 * @param source 原文件 (File source = new File("原文件(文件夹)路径")) * @param dest 复制后的目标路径 * @throws IOException */
    public static void copyFile(File source, String dest) throws IOException { 
        //创建目的地文件夹
        File destfile = new File(dest);
        if (!destfile.exists()) { 
            destfile.mkdirs();
        }
        //如果source是文件夹,则在目的地址中创建新的文件夹
        if (source.isDirectory()) { 
            File file = new File(dest+"\\"+source.getName());//用目的地址加上source的文件夹名称,创建新的文件夹
            file.mkdir();
            //得到source文件夹的所有文件及目录
            File[] files = source.listFiles();
            if (files.length==0) { 
                return;
            } else { 
                for (int i = 0 ;i<files.length;i++) { 
                    copyFile(files[i], file.getPath());
                }
            }

        }
        //source是文件,则用字节输入输出流复制文件
        else if (source.isFile()) { 
            FileInputStream fis = new FileInputStream(source);
            //创建新的文件,保存复制内容,文件名称与源文件名称一致
            File dfile = new File(dest+"\\"+source.getName());
            if (!dfile.exists()) { 
                dfile.createNewFile();
            }

            FileOutputStream fos = new FileOutputStream(dfile);
            // 读写数据
            // 定义数组
            byte[] b = new byte[1024];
            // 定义长度
            int len;
            // 循环读取
            while ((len = fis.read(b))!=-1) { 
                // 写出数据
                fos.write(b, 0 , len);
            }

            //关闭资源
            fos.close();
            fis.close();
        }
    }

    public static void main(String[] args){ 
        String sourceFilePath = "D:\\222";
        String zipFilePath = "D:\\222";
        String fileName = "333";
        boolean flag = FileToZip.fileToZip(sourceFilePath, zipFilePath, fileName);
        if(flag){ 
            System.out.println("文件打包成功!");
        }else{ 
            System.out.println("文件打包失败!");
        }
        // 能压缩文件夹的
        // FileOutputStream fos1 = new FileOutputStream(new File("D:\\222.zip"));
    	// toZip("D:\\222", fos1,true);

		// 复制文件(文件夹)
		// File source = new File("D:\\222.zip");
		// String dest = "D:\\111";
		// copyFile(source, dest)
    }

}

可以把这个当成一个工具类, 方便后续使用。压缩成压缩包两个方法都可以使用, 第一个方法fileToZip, 不能把文件夹压缩, 只能压缩文件夹下的文件。第二个方法toZip, 可以把文件夹下的所有都压缩成压缩包(KeepDirStructure要设置成true才会有压缩前的结构)。 下载完成之后记得删除压缩包, 调用delDirectory方法即可。

    原文作者:福尔摩杰
    原文地址: https://blog.csdn.net/qq_42484429/article/details/115941758
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。

相关文章