
Zip压缩多线程压缩线程池 依赖 maven坐标
压缩工具包代码 ZipCompressUtils.javaorg.apache.commons commons-compress1.20
package com.test.utils;
import org.apache.commons.compress.archivers.zip.ParallelScatterZipCreator;
import org.apache.commons.compress.archivers.zip.ZipArchiveEntry;
import org.apache.commons.compress.archivers.zip.ZipArchiveOutputStream;
import org.apache.commons.compress.parallel.InputStreamSupplier;
import org.apache.commons.io.input.NullInputStream;
import java.io.*;
import java.util.concurrent.*;
import java.util.zip.Deflater;
public class ZipCompressUtils {
public static void compressFiles(String zipOutName, String... paths) throws IOException, ExecutionException, InterruptedException {
// 创建一个线程池对象
ExecutorService executor = new ThreadPoolExecutor(5, 10, 60, TimeUnit.SECONDS, new linkedBlockingQueue<>(20), Executors.defaultThreadFactory(), new ThreadPoolExecutor.CallerRunsPolicy());
// 压缩等级默认为速度优先
compressFiles(zipOutName, executor, Deflater.BEST_SPEED, paths);
}
public static void compressFiles(String zipOutName, ExecutorService executorService, int level, String... paths) throws IOException, ExecutionException, InterruptedException {
// 创建用于多线程压缩文件的对象
ParallelScatterZipCreator parallelScatterZipCreator = new ParallelScatterZipCreator(executorService);
// 输出文件流
OutputStream outputStream = new FileOutputStream(zipOutName);
// 输出Zip文件流
ZipArchiveOutputStream zipArchiveOutputStream = new ZipArchiveOutputStream(outputStream);
// 设置压缩等级
zipArchiveOutputStream.setLevel(level);
// 设置压缩的字符编码
zipArchiveOutputStream.setEncoding("UTF-8");
// 循环压缩各个路径的文件
for (String path : paths) {
File temp = new File(path);
compress(parallelScatterZipCreator, temp, temp.getName());
}
// 将数据写入zip输出流
parallelScatterZipCreator.writeTo(zipArchiveOutputStream);
// 相关流的关闭
zipArchiveOutputStream.close();
outputStream.close();
}
public static void compressFiles(String zipOutName, ThreadFactory factory, int level, String... paths) throws IOException, ExecutionException, InterruptedException {
ExecutorService executor = new ThreadPoolExecutor(5, 10, 60, TimeUnit.SECONDS, new linkedBlockingQueue<>(20), factory, new ThreadPoolExecutor.CallerRunsPolicy());
compressFiles(zipOutName, executor, level, paths);
}
protected static void compress(ParallelScatterZipCreator parallelScatterZipCreator, File inputFile, String relativePath) throws IOException, ExecutionException, InterruptedException {
// 文件流为空,返回
if (inputFile == null) {
return;
}
// 文件为文件夹,递归遍历文件
if (inputFile.isDirectory()) {
// 获取文件内的所有文件
File[] files = inputFile.listFiles();
if (files == null) {
return;
}
// 遍历处理文件
for (File file : files) {
if (file.isDirectory()) {
compress(parallelScatterZipCreator, new File(inputFile.getAbsolutePath() + "/" + file.getName()), relativePath + "/" + file.getName());
} else {
// 转化为InputStreamSupplier对象
final InputStreamSupplier inputStreamSupplier = () -> {
try {
return new FileInputStream(file);
} catch (FileNotFoundException e) {
e.printStackTrace();
return new NullInputStream(0);
}
};
// 添加ZipArchiveEntity对象,这里的构造函数的值,name属性,是相对于zip文件内的路径
ZipArchiveEntry zipArchiveEntry = new ZipArchiveEntry(relativePath + "/" + file.getName());
// 设置压缩算法
zipArchiveEntry.setMethod(ZipArchiveEntry.DEFLATED);
// 设置未压缩文件的大小
zipArchiveEntry.setSize(file.length());
// 添加添加ZipArchiveEntity对象到多线程压缩中
parallelScatterZipCreator.addArchiveEntry(zipArchiveEntry, inputStreamSupplier);
}
}
} else {
// 当是文件时,直接处理
final InputStreamSupplier inputStreamSupplier = () -> {
try {
return new FileInputStream(inputFile);
} catch (FileNotFoundException e) {
e.printStackTrace();
return new NullInputStream(0);
}
};
ZipArchiveEntry zipArchiveEntry = new ZipArchiveEntry(relativePath + "/" + inputFile.getName());
zipArchiveEntry.setMethod(ZipArchiveEntry.DEFLATED);
zipArchiveEntry.setSize(inputFile.length());
parallelScatterZipCreator.addArchiveEntry(zipArchiveEntry, inputStreamSupplier);
}
}
}
欢迎分享,转载请注明来源:内存溢出
微信扫一扫
支付宝扫一扫
评论列表(0条)