Chủ Nhật, 10 tháng 4, 2016

4 ways to copy file in Java - 4 cách copy file trong Java

These examples illustrate how to copy contents from one file to another file. We have 4 ways in Java. 



1.  Using Java Stream

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;

/**
 *  Author : Nhu Dinh Thuan
 *          Email:nhudinhthuan@yahoo.com
 * Apr 10, 2016
 */
public class CopyFileByStream {

  public static void copy(File source, File dest) throws IOException {
    if(!dest.exists()) {
      if(!dest.getParentFile().exists()) dest.getParentFile().mkdirs();
      dest.createNewFile();
    }
    try (InputStream input = new FileInputStream(source);
        OutputStream output =new FileOutputStream(dest)){
      copy(input, output);
    }
  }

  public static void copy(InputStream input, OutputStream output) throws IOException {
    byte[] buffer = new byte[16*1024];
    int read = -1;
    while ((read = input.read(buffer)) != -1) {
      output.write(buffer, 0, read);
    }
  }

  public static void main(String[] args) {
    File sourceFile = new File("../Temp/a.html");
    File destFile = new File("../Temp/a1.html");
    try {
      copy(sourceFile, destFile);
    } catch(Exception exp) {
      exp.printStackTrace();
    }
  }
}


2. Using FileChannel

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.channels.FileChannel;

/**
 *  Author : Nhu Dinh Thuan
 *          Email:nhudinhthuan@yahoo.com
 * Apr 10, 2016
 */
public class CopyFileByChannel {

  public static void copy(File source, File dest) throws IOException {
    if(!dest.exists()) {
      if(!dest.getParentFile().exists()) dest.getParentFile().mkdirs();
      dest.createNewFile();
    }
    try (FileInputStream input = new FileInputStream(source);
        FileOutputStream output = new FileOutputStream(dest)) {
      FileChannel srcChannel = input.getChannel();
      FileChannel desChannel = output.getChannel();
      srcChannel.transferTo(0, srcChannel.size(), desChannel);
    }
  }


  public static void main(String[] args) {
    File sourceFile = new File("../Temp/a.html");
    File destFile = new File("../Temp/a2.html");
    try {
      copy(sourceFile, destFile);
    } catch(Exception exp) {
      exp.printStackTrace();
    }
  }

}

3. Using Files - NIO 2

import java.io.File;
import java.nio.file.Files;

/**
 *  Author : Nhu Dinh Thuan
 *          Email:nhudinhthuan@yahoo.com
 * Apr 10, 2016
 */
public class CopyFileByNIO2 {
  public static void main(String[] args) {
    File sourceFile = new File("../Temp/a.html");
    File destFile = new File("../Temp/a3.html");
    try {
      Files.copy(sourceFile.toPath(), destFile.toPath());
    } catch(Exception exp) {
      exp.printStackTrace();
    }
  }
}


4. Using ByteBuffer

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.nio.ByteBuffer;
import java.nio.channels.Channels;
import java.nio.channels.ReadableByteChannel;
import java.nio.channels.WritableByteChannel;

/**
 *  Author : Nhu Dinh Thuan
 *          Email:nhudinhthuan@yahoo.com
 * Apr 10, 2016
 */
public class CopyFileByByteBuffer {

  public static void copy(File source, File dest) throws IOException {
    if(!dest.exists()) {
      if(!dest.getParentFile().exists()) dest.getParentFile().mkdirs();
      dest.createNewFile();
    }

    try (FileInputStream input = new FileInputStream(source);
        FileOutputStream output = new FileOutputStream(dest)) {
      final ReadableByteChannel inputChannel = Channels.newChannel(input);
      final WritableByteChannel outputChannel = Channels.newChannel(output);
      copy(inputChannel, outputChannel);
    }
  }

  public static void copy(ReadableByteChannel src, WritableByteChannel dest) throws IOException {
    final ByteBuffer buffer = ByteBuffer.allocateDirect(16 * 1024);
    while (src.read(buffer) != -1) {
      buffer.flip();
      dest.write(buffer);
      buffer.compact();
    }
    buffer.flip();
    while (buffer.hasRemaining()) {
      dest.write(buffer);
    }
  }

  public static void main(String[] args) {
    File sourceFile = new File("../Temp/a.html");
    File destFile = new File("../Temp/a4.html");
    try {
      copy(sourceFile, destFile);
    } catch(Exception exp) {
      exp.printStackTrace();
    }
  }
}

Test Performance Code

import java.io.File;
import java.nio.file.Files;
import java.nio.file.StandardCopyOption;

/**
 *  Author : Nhu Dinh Thuan
 *          Email:nhudinhthuan@yahoo.com
 * Apr 10, 2016
 */
public class TestPerformance {
  public static void main(String[] args) {
    try {
      Thread.sleep(10*1000);


      File sourceFile = new File("../Temp/a.html");
      File destFile = new File("../Temp/new_a.html");
      
      long time = 100*1000;

      long start = System.currentTimeMillis();
      for(int i = 0; i < time; i++) {
        CopyFileByStream.copy(sourceFile, destFile);
      }
      long end = System.currentTimeMillis();
      System.out.println("Time taken by stream copy = " + (end - start));
      
      
      start = System.currentTimeMillis();
      for(int i = 0; i < time; i++) {
        CopyFileByChannel.copy(sourceFile, destFile);
      }
      end = System.currentTimeMillis();
      System.out.println("Time taken by channel copy = " + (end - start));
      
      start = System.currentTimeMillis();
      for(int i = 0; i < time; i++) {
        Files.copy(sourceFile.toPath(), destFile.toPath(), StandardCopyOption.REPLACE_EXISTING);
      }
      end = System.currentTimeMillis();
      System.out.println("Time taken by nio 2 copy = " + (end - start));
      
      start = System.currentTimeMillis();
      for(int i = 0; i < time; i++) {
        CopyFileByByteBuffer.copy(sourceFile, destFile);
      }
      end = System.currentTimeMillis();
      System.out.println("Time taken by byte buffer copy = " + (end - start));
    } catch (Exception exp) {
      exp.printStackTrace();
    }
  }

}


Output:

Time taken by stream copy = 23536
Time taken by channel copy = 22055
Time taken by nio 2 copy = 25625
Time taken by byte buffer copy = 23771

Test performance with time  = 100*1000, output:

Time taken by stream copy = 45707
Time taken by channel copy = 43815
Time taken by nio 2 copy = 50095
Time taken by byte buffer copy = 44644

Now we can see FileChannels is the best way to copy files.

This was an example that demonstrates four different ways you can copy a File in Java. Aside from, you can use Apache Commons IO library with FileUtils.

FileUtils.copyFile(sourceFile, destFile);

1 nhận xét:

  1. Bài viết rất hay. Triệu Like

    ---

    Xem tiếp bài viết cũ hơn tại đây: tháng cô hồn Những điều kiêng kị và nên làm.

    Trả lờiXóa

nhudinhthuan@gmail.com