Java IO操作——掌握壓縮流的使用(ZipOutputStream、ZipFile、ZipInputStream)[java.util包中]
阿新 • • 發佈:2019-02-20
import java.io.File ; import java.io.FileInputStream ; import java.io.InputStream ; import java.util.zip.ZipEntry ; import java.util.zip.ZipOutputStream ; import java.io.FileOutputStream ; public class ZipOutputStreamDemo02{ public static void main(String args[]) throws Exception{ // 所有異常丟擲 File file = new File("/Users/liuxun/Downloads/liuxun") ; // 定義要壓縮的資料夾 File zipFile = new File("/Users/liuxun/Downloads/liuxundir.zip") ; // 定義壓縮檔名稱 zipMultiFile("/Users/liuxun/Downloads/liuxun", "/Users/liuxun/Downloads/liuxundir.zip", true); } /* * 壓縮整個資料夾中的所有檔案,生成指定名稱的zip壓縮包 * @param filepath 檔案所在目錄 * @param zippath 壓縮後zip檔名稱 * @param dirFlag zip檔案中第一層是否包含一級目錄,true包含;false沒有 * 2015年6月9日 */ public static void zipMultiFile(String filepath ,String zippath, boolean dirFlag) { try { File file = new File(filepath);// 要被壓縮的資料夾 File zipFile = new File(zippath); ZipOutputStream zipOut = new ZipOutputStream(new FileOutputStream(zipFile)); if(file.isDirectory()){ File[] files = file.listFiles(); for(File fileSec:files){ if(dirFlag){ recursionZip(zipOut, fileSec, file.getName() + File.separator); }else{ recursionZip(zipOut, fileSec, ""); } } } zipOut.close(); } catch (Exception e) { e.printStackTrace(); } } private static void recursionZip(ZipOutputStream zipOut, File file, String baseDir) throws Exception{ if(file.isDirectory()){ File[] files = file.listFiles(); for(File fileSec:files){ recursionZip(zipOut, fileSec, baseDir + file.getName() + File.separator); } }else{ byte[] buf = new byte[1024]; InputStream input = new FileInputStream(file); zipOut.putNextEntry(new ZipEntry(baseDir + file.getName())); int len; while((len = input.read(buf)) != -1){ zipOut.write(buf, 0, len); } input.close(); } } };
ZipFile
是一個專門表示壓縮檔案的類,在JAVA中,每一個壓縮檔案都可以使用ZipFile表示,還可以使用ZipFile根據壓縮後的檔名稱找到每一個壓縮檔案中的ZipEntry並將其進行解壓縮操作。 1、public ZipFile(File file) throws ZipException,IOException 構造方法 根據File類例項化ZipFile物件。 2、public ZipEntry getEntry(String name) 根據名稱找到其對應的ZipEntry。 3、public InputStream getInputStream(ZipEntry entry) throws IOException通過ZipFile檔案,為liuxun.zip進行解壓縮操作。import java.io.File ; import java.io.FileInputStream ; import java.io.InputStream ; import java.util.zip.ZipEntry ; import java.util.zip.ZipOutputStream ; import java.util.zip.ZipFile ; import java.io.FileOutputStream ; public class ZipFileDemo01{ public static void main(String args[]) throws Exception{ // 所有異常丟擲 File file = new File("d:" + File.separator + "liuxun.zip") ; // 找到壓縮檔案 ZipFile zipFile = new ZipFile(file) ; // 例項化ZipFile物件 System.out.println("壓縮檔案的名稱:" + zipFile.getName()) ; // 得到壓縮檔案的名稱 } };
import java.io.File ;
import java.io.FileInputStream ;
import java.io.InputStream ;
import java.io.OutputStream ;
import java.util.zip.ZipEntry ;
import java.util.zip.ZipOutputStream ;
import java.util.zip.ZipFile ;
import java.io.FileOutputStream ;
public class ZipFileDemo02{
public static void main(String args[]) throws Exception{ // 所有異常丟擲
File file = new File("d:" + File.separator + "liuxun.zip") ; // 找到壓縮檔案
File outputFile = new File("d:" + File.separator + "liuxun_unzip.txt") ; // 定義解壓縮的檔名稱
ZipFile zipFile = new ZipFile(file) ; // 例項化ZipFile物件
ZipEntry entry = zipFile.getEntry("test.txt") ; // 得到一個壓縮實體
OutputStream out = new FileOutputStream(outputFile) ; // 例項化輸出流
InputStream input = zipFile.getInputStream(entry) ; // 得到一個壓縮實體的輸入流
int temp = 0 ;
while((temp=input.read())!=-1){
out.write(temp) ;
}
input.close() ; // 關閉輸入流
out.close() ; // 關閉輸出流
}
};
以上的操作中,有一個問題,必須知道壓縮檔案中的每一個壓縮實體的名稱才可以進行解壓縮操作,而現在假設要解壓一個資料夾呢?
ZipInputStream
此類的定義如下: java.lang.Object java.io.InputStream java.io.FilterInputStream java.util.zip.InflaterInputStream java.util.zip.ZipInputStream 可以不用輸入實體名稱,就可以得到每一個ZipEntry物件import java.io.File ;
import java.io.FileInputStream ;
import java.io.InputStream ;
import java.util.zip.ZipEntry ;
import java.util.zip.ZipInputStream ;
import java.io.FileInputStream ;
public class ZipInputStreamDemo01{
public static void main(String args[]) throws Exception{ // 所有異常丟擲
File zipFile = new File("d:" + File.separator + "test.zip") ; // 定義壓縮檔名稱
ZipInputStream input = null ; // 定義壓縮輸入流
input = new ZipInputStream(new FileInputStream(zipFile)) ; // 例項化ZIpInputStream
ZipEntry entry = input.getNextEntry() ; // 得到一個壓縮實體
System.out.println("壓縮實體名稱:" + entry.getName()) ;
input.close() ;
}
};
利用此特性並結合ZipFile就可以完成解壓縮資料夾的功能。
ZipFile物件,可以找到每一個ZipEntry的輸入流。但是ZipInputStream並不能得到每一個輸入流,所以需要使用ZipFile,但是ZipInputStream在取得每一個ZipEntry的時候,不需要每一個ZipEntry的名稱。
import java.io.File ;
import java.io.OutputStream ;
import java.io.InputStream ;
import java.util.zip.ZipEntry ;
import java.util.zip.ZipFile ;
import java.util.zip.ZipInputStream ;
import java.io.FileInputStream ;
import java.io.FileOutputStream ;
public class ZipInputStreamDemo02{
public static void main(String args[]) throws Exception{ // 所有異常丟擲
File file = new File("d:" + File.separator + "lx.zip") ; // 定義壓縮檔名稱
File outFile = null ; // 輸出檔案的時候要有資料夾的操作
ZipFile zipFile = new ZipFile(file) ; // 例項化ZipFile物件
ZipInputStream zipInput = null ; // 定義壓縮輸入流
OutputStream out = null ; // 定義輸出流,用於輸出每一個實體內容
InputStream input = null ; // 定義輸入流,讀取每一個ZipEntry
ZipEntry entry = null ; // 每一個壓縮實體
zipInput = new ZipInputStream(new FileInputStream(file)) ; // 例項化ZIpInputStream
while((entry = zipInput.getNextEntry())!=null){ // 得到一個壓縮實體
System.out.println("解壓縮" + entry.getName() + "檔案。") ;
outFile = new File("d:" + File.separator + entry.getName()) ; // 定義輸出的檔案路徑
if(!outFile.getParentFile().exists()){ // 如果輸出資料夾不存在
outFile.getParentFile().mkdir() ; // 建立資料夾
}
if(!outFile.exists()){ // 判斷輸出檔案是否存在
outFile.createNewFile() ; // 建立檔案
}
input = zipFile.getInputStream(entry) ; // 得到每一個實體的輸入流
out = new FileOutputStream(outFile) ; // 例項化檔案輸出流
int temp = 0 ;
while((temp=input.read())!=-1){
out.write(temp) ;
}
input.close() ; // 關閉輸入流
out.close() ; // 關閉輸出流
}
input.close() ;
}
};
如果目錄不存在,則應該進行建立操作。
總結:
1、壓縮檔案中的每一個壓縮實體都使用ZipEntry儲存,一個壓縮檔案中可能包含一個或多個ZipEntry物件。
2、在JAVA中可以進行zip、jar、gz三種格式的壓縮支援,操作流程基本上是一致的。
3、ZipOutputStream可以進行壓縮的輸出,但是輸出的位置不一定是檔案。
4、ZipFile表示每一個壓縮檔案,可以得到每一個壓縮實體的輸入流。