2013-02-26 32 views
5

Tôi muốn đọc từng dòng tệp. BufferedReader nhanh hơn nhiều so với RandomAccessFile hoặc BufferedInputStream. Nhưng vấn đề là tôi không biết có bao nhiêu byte tôi đọc. Làm thế nào để biết byte đọc (bù đắp)? Tôi đã thử.Làm thế nào để biết byte đọc (offset) của BufferedReader?

String buffer; 
int offset = 0; 

while ((buffer = br.readLine()) != null) 
    offset += buffer.getBytes().length + 1; // 1 is for line separator 

Tôi hoạt động nếu tệp nhỏ. Nhưng khi tệp lớn, bù đắp sẽ nhỏ hơn giá trị thực. Làm cách nào để tôi được bù đắp?

+0

Nhiệm vụ lớn hơn bạn đang cố gắng đạt được là gì? Đó là về cơ bản khó khăn do bộ đệm bên trong (và mã hóa, và kết thúc dòng khác nhau). –

+0

Tôi muốn có được bù đắp của sự bắt đầu của dòng. Vì vậy, tôi sử dụng bù đắp để đọc một phần của tập tin bằng cách sử dụng RandomAccessFile sau này. – user1301568

+0

Bạn giả sử rằng chỉ có một byte phân cách đường kẻ, ví dụ: \ n. Bạn có thể giả định điều đó không? – EJP

Trả lời

-3

Nếu bạn muốn đọc một dòng tập tin bằng cách dòng, tôi sẽ khuyên bạn nên mã này:

import java.io.*; 
class FileRead 
{ 
public static void main(String args[]) 
    { 
    try{ 
    // Open the file that is the first 
    // command line parameter 
    FileInputStream fstream = new FileInputStream("textfile.txt"); 
    // Use DataInputStream to read binary NOT text. 
    BufferedReader br = new BufferedReader(new InputStreamReader(fstream)); 
    String strLine; 
    //Read File Line By Line 
    while ((strLine = br.readLine()) != null) { 
    // Print the content on the console 
    System.out.println (strLine); 
    } 
    //Close the input stream 
    in.close(); 
    }catch (Exception e){//Catch exception if any 
    System.err.println("Error: " + e.getMessage()); 
    } 
    } 
} 

tôi luôn luôn sử dụng phương thức đó trong quá khứ, và hoạt động tuyệt vời!

Nguồn: Here

+2

Bạn trả lời sai một chút, vì bạn nên đóng tài nguyên bên ngoài trong một khối cuối cùng, bạn cũng không trả lời câu hỏi, và bên cạnh điều này, anh ấy đang sử dụng một cái gì đó tương tự, nhưng với một ví dụ mã nhỏ gọn hơn. – comanitza

+0

Nếu nó đến từ hoa hồng Ấn Độ, bạn nên giả sử nó chỉ là chủ yếu là đúng. Bạn nên đọc về bất kỳ trang web nào khác. –

8

Không có cách nào đơn giản để làm điều này với BufferedReader vì hai hiệu ứng: Character endcoding và kết thúc dòng. Trên Windows, dòng kết thúc là \r\n là hai byte. Trên Unix, dấu tách dòng là một byte đơn. BufferedReader sẽ xử lý cả hai trường hợp mà bạn không nhận thấy, vì vậy sau readLine(), bạn sẽ không biết số byte bị bỏ qua.

Ngoài ra buffer.getBytes() chỉ trả về kết quả chính xác khi mã hóa mặc định của bạn và mã hóa dữ liệu trong tệp vô tình xảy ra giống nhau. Khi sử dụng byte[] < ->String chuyển đổi thuộc bất kỳ loại nào, bạn nên luôn luôn chỉ định chính xác mã hóa nào sẽ được sử dụng.

Bạn cũng không thể sử dụng số đếm InputStream vì người đọc đã đọc đọc dữ liệu theo khối lớn. Vì vậy, sau khi đọc dòng đầu tiên với, nói, 5 byte, bộ đếm trong bên trong InputStream sẽ trả lại 4096 vì người đọc luôn đọc nhiều byte vào bộ đệm trong của nó.

Bạn có thể xem NIO về điều này. Bạn có thể sử dụng mức thấp ByteBuffer để theo dõi độ lệch và bọc trong CharBuffer để chuyển đổi đầu vào thành các dòng.

+0

Không có cách đơn giản để làm điều này với BufferedReader vì nó có cả đệm và phát hiện dòng mới. BTW, cảm ơn gợi ý về ByteBuffer và CharBuffer –

0

Tôi tự hỏi giải pháp cuối cùng của bạn, tuy nhiên, tôi nghĩ rằng việc sử dụng loại dài thay vì int có thể đáp ứng hầu hết trường hợp trong mã của bạn ở trên.

Các vấn đề liên quan