思路:获取解压文件路径,指定解压后存放路径,
在方法中,首先创建一个目标目录(如果不存在),然后使用ZipInputStream来逐个读取zip文件中的条目。对于每个条目,它检查是否是一个目录,如果是则创建相应的目录,如果不是则调用extractFile方法来提取文件。
在提取文件时,它会增加解压缩的文件数量,并计算解压进度,然后输出当前的解压进度信息。
/**
* 解压zip文件
* @param zipFilePath 解压文件路径
* @param destDirectory 解压后文件存放位置
*/
public static void decompression(String zipFilePath ,String destDirectory ) {
try {
int totalFiles = 0;
try (ZipInputStream zipIn = new ZipInputStream(new FileInputStream(zipFilePath), getCharset(zipFilePath))) {
ZipEntry entry;
while ((entry = zipIn.getNextEntry()) != null) {
// 获取压缩文件中的总文件数量
totalFiles++;
}
}
unzip(zipFilePath, destDirectory, totalFiles);
System.out.println("解压缩完成!");
} catch (IOException e) {
System.out.println("解压缩出错: " + e.getMessage());
}
}
public static void unzip(String zipFilePath, String destDirectory, int totalFiles) throws IOException {
int fileCount = 0; // 解压缩的文件数量
File destDir = new File(destDirectory);
if (!destDir.exists()) {
destDir.mkdir();
}
try (ZipInputStream zipIn = new ZipInputStream(new FileInputStream(zipFilePath), getCharset(zipFilePath))) {
ZipEntry entry;
while ((entry = zipIn.getNextEntry()) != null) {
String filePath = destDirectory + File.separator + entry.getName();
if (entry.isDirectory()) {
File dir = new File(filePath);
dir.mkdirs();
} else {
extractFile(zipIn, filePath);
// 增加解压缩的文件数量
fileCount++;
// 计算解压进度
double progress = (double) fileCount / (double) totalFiles * 100.0;
System.out.println("当前解压进度: "+ zipFilePath + (int)progress + "%");
}
zipIn.closeEntry();
}
}
}
private static void extractFile(ZipInputStream zipIn, String filePath) throws IOException {
try (FileOutputStream fos = new FileOutputStream(filePath)) {
byte[] buffer = new byte[1024];
int bytesRead;
while ((bytesRead = zipIn.read(buffer)) != -1) {
fos.write(buffer, 0, bytesRead);
}
}
}
private static Charset getCharset(String zipFilePath) throws IOException {
try (BufferedInputStream bis = new BufferedInputStream(new FileInputStream(zipFilePath))) {
int test = bis.read();
int secondTest = bis.read();
if (test == 0xEF && secondTest == 0xBB) {
return StandardCharsets.UTF_8;
} else {
return Charset.forName("GBK");
}
}
}