java使用IO流完成檔案的複製(文字、圖片、視訊)
阿新 • • 發佈:2019-01-08
一、使用位元組流實現
複製檔案中的地址可以是圖片或視訊。
1.基礎版:
package com.uwo9.test01; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; public class Test08 { public static void main(String[] args) { long startTime = System.currentTimeMillis(); // 被複制的檔案 File fromFile = new File("E:/Temp/1.jpg"); // 複製出來的檔案 File toFile = new File("E:/Temp/2.jpg"); // 宣告入流 InputStream is = null; // OutputStream os=null; try { is = new FileInputStream(fromFile);//建立輸入流 os = new FileOutputStream(toFile);// 建立輸出流 // 逐個位元組讀取 int content = is.read(); while (content != -1) { // System.out.print((char)content); 控制檯 // 使用輸出流將讀取到的content寫入檔案 os.write(content); // 重新整理流 // os.flush(); content = is.read(); } } catch (FileNotFoundException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); }finally { // 關閉流 try { is.close(); os.close(); } catch (IOException e) { e.printStackTrace(); } long endTime = System.currentTimeMillis(); long costTime = endTime - startTime; System.out.println("複製檔案完成,耗時:" + costTime + "毫秒"); } } }
發現問題:我們發現,上面的方法,可以實現複製功能,但複製的檔案比較大時,複製比較慢
2.第一次優化:
我們可以用位元組陣列來做緩衝區,提升效率。
package com.uwo9.test01; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; public class Test08 { public static void main(String[] args) { long startTime = System.currentTimeMillis(); // 被複制的檔案 File fromFile = new File("E:/Temp/1.avi"); // 複製出來的檔案 File toFile = new File("E:/Temp/2.avi"); // 宣告入流 InputStream is = null; // OutputStream os = null; try { is = new FileInputStream(fromFile);// 建立輸入流 os = new FileOutputStream(toFile);// 建立輸出流 // 建立用來做緩衝區的位元組陣列 byte[] array = new byte[512]; // 將陣列讀取到array中,count記錄的為讀取陣列中位元組數 int count = is.read(array); while (count != -1) { // 使用輸出流將讀取到的content寫入檔案 // os.write(array); // 將讀取到的有效資料寫入檔案 os.write(array, 0, count); // 重新整理流 // os.flush(); count = is.read(array); } } catch (FileNotFoundException e) { e.printStackTrace(); } catch (IOException e) { e.printStackTrace(); } finally { // 關閉流 try { is.close(); os.close(); } catch (IOException e) { e.printStackTrace(); } long endTime = System.currentTimeMillis(); long costTime = endTime - startTime; System.out.println("複製檔案完成,耗時:" + costTime + "毫秒"); } } }
發現問題:效率提升了,但我們java裡是否有更好的實現方法呢
3.第二次優化:
我們可以加入緩衝字元流
節點流與處理流(包裝流):
1.節點流:可以直接從資料來源或目的地讀寫資料。節點流處於IO操作的第一線,所有操作必須通過他們進行。
2.處理流:不能直接連線到資料來源或目的地,是其他流進行封裝。目的是主要是簡化操作和提高效能。處理流可以對其他流進行處理(提高效率或操作靈活性)。
package com.uwo9.test01; import java.io.BufferedInputStream; import java.io.BufferedOutputStream; import java.io.File; import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; public class Test08 { public static void main(String[] args) { long startTime = System.currentTimeMillis(); File fromFile = new File("E:/Temp/1.avi"); File toFile = new File("E:/Temp/2.avi"); InputStream is = null; OutputStream os = null; BufferedInputStream bis = null; BufferedOutputStream bos = null; try { is = new FileInputStream(fromFile); os = new FileOutputStream(toFile); // 建立緩衝流 bis = new BufferedInputStream(is); bos = new BufferedOutputStream(os); int content = bis.read(); while (content != -1) { // 使用緩衝流寫資料 bos.write(content); // 重新整理 bos.flush(); content = bis.read(); } } catch (FileNotFoundException e) { e.printStackTrace(); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } finally { try { is.close(); os.close(); } catch (IOException e) { e.printStackTrace(); } } long endTime = System.currentTimeMillis(); System.out.println("視訊複製完成,耗時:" + (endTime - startTime) + "毫秒"); } }
發現問題:我們還想繼續提升效率
4.第三次優化:
我們可以在緩衝流的基礎上再加位元組陣列來做緩衝區,提升效率
package com.uwo9.test01;
import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
public class Test08 {
public static void main(String[] args) {
long startTime = System.currentTimeMillis();
File fromFile = new File("E:/Temp/1.avi");
File toFile = new File("E:/Temp/2.avi");
InputStream is = null;
OutputStream os = null;
BufferedInputStream bis = null;
BufferedOutputStream bos = null;
try {
is = new FileInputStream(fromFile);
os = new FileOutputStream(toFile);
// 建立緩衝流
bis = new BufferedInputStream(is);
bos = new BufferedOutputStream(os);
byte[]buffer = new byte[8192];
int count = bis.read(buffer);
while(count != -1){
//使用緩衝流寫資料
bos.write(buffer,0,count);
//重新整理
bos.flush();
count = bis.read(buffer);
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
is.close();
os.close();
} catch (IOException e) {
e.printStackTrace();
}
}
long endTime = System.currentTimeMillis();
System.out.println("視訊複製完成,耗時:" + (endTime - startTime) + "毫秒");
}
}
我們會發現,效率再次大大提升。
二、使用字元流
1.基礎版
package com.uwo9.test01;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.io.Reader;
import java.io.Writer;
public class Test08 {
public static void main(String[] args) {
long startTime = System.currentTimeMillis();
//1.建立檔案物件
File fromFile = new File("E:/Temp/Test1.java");
File toFile = new File("E:/Temp/Test2.java");
//2.建立字元輸入流
Reader reader=null;
Writer writer=null;
try {
reader = new FileReader(fromFile);
writer = new FileWriter(toFile);
//3.迴圈讀取(列印)
int content = reader.read();
while(content != -1){
//將字元寫入檔案
writer.write(content);
//繼續讀取
content = reader.read();
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}finally {
//4.關閉流
try {
reader.close();
writer.close();
} catch (IOException e) {
e.printStackTrace();
}
}
long endTime = System.currentTimeMillis();
System.out.println("複製完成,耗時:"+(endTime-startTime)+"毫秒");
}
}
發現問題:我們發現,字元流複製二進位制普通文字型別的檔案沒問題,但讀取圖片、視訊檔案時,會出現丟幀、檔案損壞現象。
2.優化普通二進位制文字檔案方法
我們可以使用包裝流(處理流),及其特有的逐行讀取方法提升效率
package com.uwo9.test01;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileReader;
import java.io.FileWriter;
import java.io.IOException;
import java.io.Reader;
import java.io.Writer;
public class Test08 {
public static void main(String[] args) {
long startTime = System.currentTimeMillis();
File fromFile = new File("E:/Temp/Test1.java");
File toFile = new File("E:/Temp/Test1.java");
Reader reader = null;
Writer writer = null;
BufferedReader br = null;
BufferedWriter bw = null;
try {
reader = new FileReader(fromFile);
writer = new FileWriter(toFile);
br = new BufferedReader(reader);
bw = new BufferedWriter(writer);
String content = br.readLine();//讀取一行
while (content != null) {
bw.write(content);
// 換行操作
bw.newLine();
bw.flush();
content = br.readLine();
}
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
reader.close();
writer.close();
} catch (IOException e) {
e.printStackTrace();
}
}
long endTime = System.currentTimeMillis();
System.out.println("檔案複製完成,耗時:" + (endTime - startTime) + "毫秒");
}
}
FileWriter(File file, boolean append)
FileOutputStream(File file, boolean append)