209

FileReaderにラップされたBufferedReaderを使用してローカルファイルを読み取っています。

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

私もそうする必要がありclose()ますFileReaderか、それともラッパーがそれを処理しますか?私は人々がこのようなことをするコードを見てきました:

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

このメソッドはサーブレットから呼び出されます。ハンドルを開いたままにしないようにしたいと思います。

4

10 に答える 10

216

番号。

BufferedReader.close()

BufferedReaderおよびInputStreamReaderのjavadocに従ってストリームを閉じます

と同様

FileReader.close()

します。

于 2009-09-07T10:20:10.323 に答える
112

他の人が指摘しているように、外側のラッパーを閉じるだけで済みます。

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

BufferedReaderコンストラクターが例外をスローした場合(たとえば)、これがファイルハンドルをリークする可能性は非常に低いですOutOfMemoryError。アプリがこの状態にある場合、クリーンアップにどれだけ注意を払う必要があるかは、OSから他のプログラムに割り当てたいリソースを奪わないことがどれほど重要かによって異なります。

Java 5または6でラッパーコンストラクターが失敗する可能性がある場合は、Closeableインターフェースを使用できます。

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

Java 7コードは、try-with-resourcesパターンを使用する必要があります。

try (Reader reader = new FileReader(fileName);
    BufferedReader buffered = new BufferedReader(reader)) {
  // TODO: input
}
于 2009-09-07T10:57:08.317 に答える
7

BufferedReaderのソースコードは、BufferedReaderを閉じると原資産が閉じられることを示しています。

于 2009-09-07T10:20:11.310 に答える
6

BufferedReaderのソースによると、この場合bReader.closeはfReader.closeを呼び出すため、技術的には後者を呼び出す必要はありません。

于 2009-09-07T10:19:57.533 に答える
6

ソースコードを確認したところ、例として次のことがわかりました。

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

BufferedReaderオブジェクトのclose ()メソッドは、 Readerクラスのabstract close()メソッドを呼び出し、最終的にInputStreamReaderクラスに実装されたメソッドを呼び出し、 InputStreamオブジェクトを閉じます。

したがって、bReader.close()だけで十分です。

于 2015-09-02T18:00:08.940 に答える
3

Java 7以降では、try-with-resourcesステートメントを使用できます。

try (BufferedReader br = new BufferedReader(new FileReader(path))) {
    return br.readLine();
}

インスタンスはtry-with-resourceステートメントで宣言されているためBufferedReader、tryステートメントが正常に完了するか突然完了するかに関係なく、インスタンスは閉じられます。finallyしたがって、ステートメントで自分で閉じる必要はありません。(これは、ネストされたリソースステートメントの場合にも当てはまります)

これは、リソースを操作するための推奨される方法です。詳細については、ドキュメントを参照してください。

于 2018-08-03T08:12:28.343 に答える
0

bufferedReader、つまりreader.close()を閉じるだけで、正常に動作します。

于 2015-02-12T20:49:46.063 に答える
0

私は遅れていますが:

BufferReader.java:

public BufferedReader(Reader in) {
  this(in, defaultCharBufferSize);
}

(...)

public void close() throws IOException {
    synchronized (lock) {
        if (in == null)
            return;
        try {
            in.close();
        } finally {
            in = null;
            cb = null;
        }
    }
}
于 2018-12-07T19:56:14.317 に答える
0

ラップされたリーダー/ライターを閉じる必要はありません。

ドキュメント(Reader.close()Writer.close())を確認すると、次のように表示されReader.close()ます。

ストリームを閉じて、それに関連付けられているシステムリソースを解放します。

これは、「それに関連するすべてのシステムリソースを解放する」と言っているだけです。それは確認されませんが..それはあなたにもっと深く見始めるためのナッジを与えます。そしてあなたがそれに行くならば、Writer.close()それはそれ自身を閉じるとだけ述べます。

そのような場合は、OpenJDKを参照してソースコードを確認します。

BufferedWriterの265行目にはが表示されますout.close()。だからそれはそれ自体を閉じていません..それは別のものです。クラスで""の出現を検索すると、ライターである行87outのコンストラクターで、クラスが別のコンストラクターを呼び出し、パラメーターを独自の変数に割り当てる場所をラップしていることがわかります。outoutout

だから..他の人はどうですか?同様のコードは、BufferedReader Line 514BufferedInputStream Line 468InputStreamReaderLine199で確認できます。他の私は知りませんが、これは彼らが知っていると仮定するのに十分なはずです。

于 2019-05-02T10:08:39.657 に答える
0

シナリオ内でのみ閉じる必要がありBufferedReaderます。

他の人が指摘しているように、JavaDocsはあいまいです。closeすぐに呼び出されたい場合は、try-with-resourcesブロックを使用するのが最善の方法ですが、リーダーを開いたままにする必要がある場合は機能しません(たとえば、基礎となる読者-通常、そこに電話をかけるのは発信者の責任closeです)。

ソースコードにアクセスできず、リーダーとJVMがclose状況に応じてさまざまなリーダーとストリームを呼び出すかどうかを確認したい場合はclose、簡単なテストとしてメソッドをオーバーライドできます。

Path path = Paths.get("/home/example/test.txt");

InputStream fileInputStream = new FileInputStream(path.toFile()) {
    public void close() throws IOException {
        System.out.println("FileInputStream::close()");
        super.close();
    }
};
Reader inputStreamReader = new InputStreamReader(fileInputStream, Charsets.UTF_8) {
    public void close() throws IOException {
        System.out.println("InputStreamReader::close()");
        super.close();
    }
};
BufferedReader bufferedReader = new BufferedReader(inputStreamReader) {
    public void close() throws IOException {
        System.out.println("BufferedReader::close()");
        super.close();
    }
};

bufferedReader.close();

上記を実行すると、次のようなものが表示されます。

BufferedReader::close()
InputStreamReader::close()
FileInputStream::close()

JavaDocには明示的な仕様が記述されていないため、すべてのJVMでの動作を確認することはできません。ただし、ほとんどのリーダー/ストリームは上記のパターンに従っているようです(たとえばGZIPInputStream、上記の例にを追加して、それGZIPInputStream::close()が呼び出されることを確認できます)。

于 2021-10-11T15:01:41.817 に答える