2009-09-07 45 views
152

Tôi đang đọc một tập tin địa phương sử dụng một BufferedReader quấn quanh một FileReader:Tôi có cần đóng() cả FileReader và BufferedReader không?

BufferedReader reader = new BufferedReader(new FileReader(fileName)); 
// read the file 
// (error handling snipped) 
reader.close(); 

Tôi có cần phải close() các FileReader là tốt, hoặc wrapper sẽ xử lý đó? Tôi đã nhìn thấy mã nơi mọi người làm một cái gì đó như thế này:

FileReader fReader = new FileReader(fileName); 
BufferedReader bReader = new BufferedReader(fReader); 
// read the file 
// (error handling snipped) 
bReader.close(); 
fReader.close(); 

Phương pháp này được gọi từ một servlet, và tôi muốn chắc chắn rằng tôi không để lại bất kỳ tay cầm mở.

+4

Bạn biết đấy, bạn chỉ có thể đọc nguồn thông tin như thế này. Tất cả đều có trong src.zip trong thư mục cài đặt JDK, hoặc bạn có thể đọc nó trực tuyến tại ví dụ http://www.docjar.com/html/api/java/io/BufferedReader.java.html – gustafc

+36

Nói cho ai đó đọc nguồn là tồi tệ hơn nói "RTFM!". Và nếu nguồn có lỗi; ngầm chúng ta muốn biết hành vi * đúng * là gì? – Raedwald

+1

Vâng ... từ quan điểm này: chỉ đến các thông số kỹ thuật API không phải là tốt hơn sau đó. Nếu nguồn không có lỗi gây ra rằng nó không hoạt động như nó được chỉ định trong tài liệu, bạn không thể dựa vào tài liệu. Vì vậy, không có cách nào tốt để trả lời một câu hỏi như vậy. – Atmocreations

Trả lời

179

không.

BufferedReader.close() 

đóng dòng theo javadoc cho BufferedReaderInputStreamReader

cũng như

FileReader.close() 

làm.

+7

+1 để kết hợp tính gọn gàng và rõ ràng. – CPerkins

+11

Trừ khi hàm tạo đến 'BufferedReader' ném một ngoại lệ. Đó là sạch hơn chỉ để đóng dòng cơ bản, mặc dù bạn cần phải xem ra cho trang trí với các nguồn lực và đệm. –

+6

Javadoc không nói liệu 'BufferedReader.close()' có đóng trình đọc cơ bản hay không. Mô tả của nó được sao chép đơn giản từ 'Reader.close()'. Đây có thể là hành vi thực tế trong thực tế, nhưng nó không được ghi lại. –

6

Theo nguồn BufferedReader, trong trường hợp này là bReader.close gọi fReader.close vì vậy về mặt kỹ thuật, bạn không phải gọi hàm sau.

4

Mã nguồn cho BufferedReader cho biết rằng phần dưới được đóng khi bạn đóng BufferedReader.

+0

Tôi thực sự muốn đưa ra điều này để liên kết với một cái gì đó cụ thể, nhưng điều này chỉ đề cập đến việc thực hiện OpenJDK, và vì JavaDocs không rõ ràng cho 'Reader # close()', điều này không cung cấp bằng chứng cụ thể rằng Oracle JDK , ví dụ, được thực hiện theo cách tương tự. – searchengine27

83

Khi những người khác đã chỉ ra, bạn chỉ cần đóng trình bao bọc bên ngoài.

BufferedReader reader = new BufferedReader(new FileReader(fileName)); 

Có một cơ hội rất mỏng mà điều này có thể bị rò rỉ một tập tin xử lý nếu các nhà xây dựng BufferedReader ném một ngoại lệ (ví dụ OutOfMemoryError). Nếu ứng dụng của bạn ở trạng thái này, mức độ làm sạch của bạn cần phải phụ thuộc vào mức độ nghiêm trọng của việc bạn không tước đoạt hệ điều hành của tài nguyên mà nó có thể muốn phân bổ cho các chương trình khác.

Giao diện Closeable có thể được sử dụng nếu một constructor wrapper là khả năng thất bại trong Java 5 hoặc 6:

Reader reader = new FileReader(fileName); 
Closeable resource = reader; 
try { 
    BufferedReader buffered = new BufferedReader(reader); 
    resource = buffered; 
    // TODO: input 
} finally { 
    resource.close(); 
} 

Java 7 mã nên sử dụng try-với-nguồn mẫu:

try (Reader reader = new FileReader(fileName); 
    BufferedReader buffered = new BufferedReader(reader)) { 
    // TODO: input 
} 
+3

Cảm ơn bạn, điều đó rất sáng suốt. – Zilk

+0

Trong cùng một tĩnh mạch: http://stackoverflow.com/a/2732760/281545 –

0

Bạn chỉ cần đóng bộ đệm bufferedReader ie.close() và nó sẽ hoạt động tốt.

3

Sau khi kiểm tra mã nguồn, tôi thấy rằng cho ví dụ:

FileReader fReader = new FileReader(fileName); 
BufferedReader bReader = new BufferedReader(fReader); 

phương pháp chặt chẽ() trên BufferedReader đối tượng sẽ gọi phương thức đóng trừu tượng() của đọc lớp mà sẽ cuối cùng gọi phương thức được triển khai trong lớp InputStreamReader, sau đó đóng đối tượng InputStream.

Vì vậy, chỉ bReader.close() là đủ.

+1

Nội dung mã nguồn không hiển thị như một tham chiếu. Đó là những gì các * đặc điểm kỹ thuật * nói, trong trường hợp này là Javadoc, có thể được dựa vào. – EJP

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