Tags:

So sánh tốc độ đọc file giữa FileInputStream, BufferedInputStream, FileReader và BufferedReader

Trong bài viết này mình đã tổng hợp một số cách thường sử dụng để đọc file text. Vậy cách nào trong đó sẽ có tốc độ thực thi nhanh nhất để chúng ta lựa chọn cho dự án?

Trong bài viết này mình sẽ thử so sánh thời gian đọc file text của FileInputStream, BufferedInputStream, FileReader, BufferedReader để xen thằng nào nhanh nhất nhé.

Thí nghiệm 

Cho 4 thằng FileInputStream, BufferedInputStream, FileReader, BufferedReader đọc cùng một file text có độ dài lớn. 

File text được sử dụng trong thử nghiệm là file từ điển Việt-Anh trích từ nguồn http://www.denisowski.org/Vietnamese/vnedict.txt.

Các bước thực hiện:

  • B1: Triển khai các method đọc file theo từng byte/char.
  • B2: Tiến hành đo thời gian đọc file của các đối tượng FileInputStream, BufferedInputStream, FileReader, BufferedReader.
  • B3: Thực hiện bước 2 N lần và lưu các kết quả vào mảng.
  • B4: Tính thời gian trung bình dựa vào kết quả được lưu trong mảng và ghi vào file output.txt.

Triển khai

Tiến hành triển khai các method đọc file cho từng đối tượng cụ thể:

FileInputStream

import java.io.IOException;

public class FileInputStream {
    /**
     *  Param: pathname to readfile
     *  Return: time execution: milis
     */
    public static long read(String pathName) {
        long start = System.currentTimeMillis();

        try (java.io.FileInputStream fin = new java.io.FileInputStream(pathName)) {
            int data = fin.read();
            while (data != -1) {
                data = fin.read();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        long end = System.currentTimeMillis();
        return end - start;
    }
}

BufferedInputStream

BufferedInputStream các bạn có thể chỉnh sửa lại kích thước của bộ nhớ đệm. Lưu ý với các kích thước khác nhau thì chúng ta có thể nhận được thời gian thực thi khác nhau. Ở đây mình lấy mặc định là 8192.

import java.io.IOException;

public class BufferedInputStream {
    /**
     *  Param:
     *      + pathname file
     *      + sizeBuffered
     *  Return: time execution: milis
     */
    public static long read(String pathName, int sizeBuffered) {
        long start = System.currentTimeMillis();
        try (java.io.BufferedInputStream fin = new java.io.BufferedInputStream(new java.io.FileInputStream(pathName), sizeBuffered)) {
            int data = fin.read();
            while (data != -1) {
                data = fin.read();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        long end = System.currentTimeMillis();
        return end - start;
    }
}

FileReader

import java.io.IOException;

public class FileReader {
    /**
     * Param:
     * + pathname file
     * Return: time execution: milis
     */
    public static long read(String pathName) {
        long start = System.currentTimeMillis();

        try (java.io.FileReader fin = new java.io.FileReader(pathName)) {
            int data = fin.read();
            while (data != -1) {
                data = fin.read();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        long end = System.currentTimeMillis();
        return end - start;
    }
}

BufferedReader

BufferedReader các bạn có thể chỉnh sửa lại kích thước của bộ nhớ đệm. Lưu ý với các kích thước khác nhau thì chúng ta có thể nhận được thời gian thực thi khác nhau. Ở đây mình lấy mặc định là 8192.

import java.io.IOException;

public class BufferedReader {

    /**
     * Param:
     * + pathname file
     * Return: time execution: milis
     */
    public static long read(String pathName, int size) {
        long start = System.currentTimeMillis();

        try (java.io.BufferedReader fin = new java.io.BufferedReader(new java.io.FileReader(pathName), size)) {
            int data = fin.read();
            while (data != -1) {
                data = fin.read();
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        long end = System.currentTimeMillis();
        return end - start;
    }
}

Chạy thử và đo thời gian

Cho số lần thực hiện là 100, với mỗi lần thực thi sẽ lưu kết quả vào mảng. Sau khi thực hiện xong 100 lần thì tiến hành tính thời gian trung bình dựa trên kết quả được lưu trong mảng và ghi vào file output.

import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;

public class Main {

    public static void main(String[] args) {
        BufferedWriter bufferedWriter = null;
        try {
            String pathName = "./src/vnedict.txt";
            String output = "./src/output.txt";

            int n = 100;
            long[] averageTimeFileInputStream = new long[n];
            long[] averageTimeBufferedInputStream = new long[n];
            long[] averageTimeFileReader = new long[n];
            long[] averageTimeBufferedReader = new long[n];

            bufferedWriter = new BufferedWriter(new FileWriter(output));

            System.out.println("STARTING");
            System.out.println("--------------------------------");

            for (int i = 0; i < n; i++) {
                System.out.println("Reading at times: " + (i + 1));
                averageTimeFileInputStream[i] = FileInputStream.read(pathName);
                averageTimeBufferedInputStream[i] = BufferedInputStream.read(pathName, 8192);
                averageTimeFileReader[i] = FileReader.read(pathName);
                averageTimeBufferedReader[i] = BufferedReader.read(pathName, 8192);
            }

            bufferedWriter.write("The average time of FileInputStream: " + averageTime(averageTimeFileInputStream, n) + "ms");
            bufferedWriter.newLine();
            bufferedWriter.write("The average time of BufferedInputStream: " + averageTime(averageTimeBufferedInputStream, n) + "ms");
            bufferedWriter.newLine();
            bufferedWriter.write("The average time of FileReader: " + averageTime(averageTimeFileReader, n) + "ms");
            bufferedWriter.newLine();
            bufferedWriter.write("The average time of BufferedReader: " + averageTime(averageTimeBufferedReader, n) + "ms");
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                if (bufferedWriter != null) {
                    bufferedWriter.close();
                }
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    public static double averageTime(long[] arr, int n) {
        double sum = 0;
        for (long e : arr)
            sum += e;
        return sum / n;
    }

}

Output:

Reading at times: 85
Reading at times: 86
Reading at times: 87
Reading at times: 88
Reading at times: 89
Reading at times: 90
Reading at times: 91
Reading at times: 92
Reading at times: 93
Reading at times: 94
Reading at times: 95
Reading at times: 96
Reading at times: 97
Reading at times: 98
Reading at times: 99
Reading at times: 100

The average time of FileInputStream: 1839.62ms
The average time of BufferedInputStream: 6.19ms
The average time of FileReader: 39.22ms
The average time of BufferedReader: 15.33ms

Với kết quả trên thì chúng ta có thể dễ dàng nhìn thấy BufferedInputStream có tốc độ đọc nhanh nhất, nhanh gấp đôi so với BufferedReader.

Bên cạnh đó chúng ta cũng thấy rằng FileInputStream tốn rất nhiều thời gian để đọc file.

Mặc dù BufferedReader có thời gian đọc chậm hơn so với BufferedInputStream thế nhưng BufferedReader lại có rất nhiều method hỗ trợ cho việc đọc file text như readLine() – đọc từng dòng, read(char[] c) – đọc mảng ký tự etc.

Source code và file từ điển cho các bạn tham khảo.

0 0 votes
Article Rating
Subscribe
Notify of
guest
2 Comments
Newest
Oldest Most Voted
Inline Feedbacks
View all comments
2
0
Would love your thoughts, please comment.x
()
x