Cari Bilangan Garisan dalam Fail Menggunakan Java

1. Gambaran keseluruhan

Dalam tutorial ini, kita akan belajar bagaimana mencari jumlah baris dalam file menggunakan Java dengan bantuan API IO Java standard, Google Guav a dan perpustakaan Apache Commons IO .

2. Fail NIO2

Perhatikan bahawa, di seluruh tutorial ini, kita akan menggunakan nilai contoh berikut sebagai nama fail input dan jumlah baris:

static final String INPUT_FILE_NAME = "src/main/resources/input.txt"; static final int NO_OF_LINES = 45; 

Java 7 memperkenalkan banyak peningkatan pada perpustakaan IO yang ada dan membungkusnya di bawah NIO2:

Mari mulakan dengan Files dan lihat bagaimana kita dapat menggunakan APInya untuk mengira bilangan baris:

@Test public void whenUsingNIOFiles_thenReturnTotalNumberOfLines() throws IOException { try (Stream fileStream = Files.lines(Paths.get(INPUT_FILE_NAME))) { int noOfLines = (int) fileStream.count(); assertEquals(NO_OF_LINES, noOfLines); } }

Atau dengan hanya menggunakan kaedah Files # readAllLines :

@Test public void whenUsingNIOFilesReadAllLines_thenReturnTotalNumberOfLines() throws IOException { List fileStream = Files.readAllLines(Paths.get(INPUT_FILE_NAME)); int noOfLines = fileStream.size(); assertEquals(NO_OF_LINES, noOfLines); }

3. NIO FileChannel

Sekarang mari kita periksa FileChannel, alternatif Java NIO berprestasi tinggi untuk membaca bilangan baris:

@Test public void whenUsingNIOFileChannel_thenReturnTotalNumberOfLines() throws IOException { int noOfLines = 1; try (FileChannel channel = FileChannel.open(Paths.get(INPUT_FILE_NAME), StandardOpenOption.READ)) { ByteBuffer byteBuffer = channel.map(MapMode.READ_ONLY, 0, channel.size()); while (byteBuffer.hasRemaining()) { byte currentByte = byteBuffer.get(); if (currentByte == '\n') noOfLines++; } } assertEquals(NO_OF_LINES, noOfLines); }

Walaupun FileChannel diperkenalkan di JDK 4, penyelesaian di atas hanya berfungsi dengan JDK 7 atau lebih tinggi .

4. Fail Jambu Batu Google

Perpustakaan pihak ketiga alternatif adalah kelas Google Guava Files . Kelas ini juga dapat digunakan untuk menghitung jumlah baris dengan cara yang serupa dengan yang kita lihat dengan Files # readAllLines .

Mari mulakan dengan menambahkan kebergantungan jambu batu di pom.xml kami :

 com.google.guava guava 28.0-jre 

Dan kemudian kita boleh menggunakan readLines untuk mendapatkan Senarai baris fail:

@Test public void whenUsingGoogleGuava_thenReturnTotalNumberOfLines() throws IOException { List lineItems = Files.readLines(Paths.get(INPUT_FILE_NAME) .toFile(), Charset.defaultCharset()); int noOfLines = lineItems.size(); assertEquals(NO_OF_LINES, noOfLines); }

5. Apache Commons IO FileUtils

Sekarang, mari kita lihat API Apache Commons IO FileUtils , penyelesaian sejajar dengan Jambu Batu.

Untuk menggunakan perpustakaan, kita harus memasukkan kebergantungan commons-io dalam pom.xml :

 commons-io commons-io 2.6 

Pada ketika itu, kita dapat menggunakan FileUtils # lineIterator Apache Commons IO , yang membersihkan beberapa pengendalian fail untuk kita:

@Test public void whenUsingApacheCommonsIO_thenReturnTotalNumberOfLines() throws IOException { int noOfLines = 0; LineIterator lineIterator = FileUtils.lineIterator(new File(INPUT_FILE_NAME)); while (lineIterator.hasNext()) { lineIterator.nextLine(); noOfLines++; } assertEquals(NO_OF_LINES, noOfLines); }

Seperti yang dapat kita lihat, ini sedikit lebih verbose daripada penyelesaian Google Guava.

6. BufferedReader

Jadi, bagaimana dengan cara sekolah lama? Sekiranya kita tidak berada di JDK 7 dan kita tidak dapat menggunakan perpustakaan pihak ketiga, kita mempunyai BufferedReader :

@Test public void whenUsingBufferedReader_thenReturnTotalNumberOfLines() throws IOException { int noOfLines = 0; try (BufferedReader reader = new BufferedReader(new FileReader(INPUT_FILE_NAME))) { while (reader.readLine() != null) { noOfLines++; } } assertEquals(NO_OF_LINES, noOfLines); }

7. LineNumberReader

Atau, kita boleh menggunakan LineNumberReader, subkelas langsung BufferedReader , yang sedikit kurang verbose:

@Test public void whenUsingLineNumberReader_thenReturnTotalNumberOfLines() throws IOException { try (LineNumberReader reader = new LineNumberReader(new FileReader(INPUT_FILE_NAME))) { reader.skip(Integer.MAX_VALUE); int noOfLines = reader.getLineNumber() + 1; assertEquals(NO_OF_LINES, noOfLines); } }

Di sini kita memanggil kaedah langkau untuk pergi ke akhir fail, dan kita menambah 1 pada jumlah baris yang dihitung sejak penomboran baris bermula pada 0.

8. Pengimbas

Dan akhirnya, jika kita sudah menggunakan Scanner sebagai sebahagian daripada penyelesaian yang lebih besar, ia juga dapat menyelesaikan masalahnya:

@Test public void whenUsingScanner_thenReturnTotalNumberOfLines() throws IOException { try (Scanner scanner = new Scanner(new FileReader(INPUT_FILE_NAME))) { int noOfLines = 0; while (scanner.hasNextLine()) { scanner.nextLine(); noOfLines++; } assertEquals(NO_OF_LINES, noOfLines); } }

9. Kesimpulannya

Dalam tutorial ini, kami telah meneroka pelbagai cara untuk mencari bilangan baris dalam fail menggunakan Java. Oleh kerana tujuan utama semua API ini bukan untuk menghitung jumlah baris dalam fail, disarankan memilih penyelesaian yang tepat untuk keperluan kita.

Seperti biasa, kod sumber untuk tutorial ini terdapat di GitHub.