リーダーを使用するメソッドがあり、スキャナーを使用してリーダーで操作したい場合:
Scanner scanner = new Scanner(reader);
while(scanner.hasNext()) {
//blah blah blah
}
scanner
を閉じないのは安全ですか?ドキュメントには、「このスキャナーを閉じる」と書かれており、基礎となる読み取り可能ファイルを閉じることについて説明しています。読み取り可能ファイルを閉じたくないので、代わりに呼び出し側に準備ができたらreader
を閉じたいとします。ここでscanner
を閉じない方が安全ですか?
それはあなたが何に対して安全になりたいかによります。
基になるストリームが閉じていることを確認しようとしている場合は、どちらのアプローチでも問題ありません。
Scanner
をクローズとしてマークする場合(オブジェクトに対する後続のすべての操作がすぐに失敗するように)、Scanner.close()
を呼び出す必要があります。
これは一般的な原則です。つまり、メモリ内のバッファリングを何らかの方法で行うさまざまな種類のストリームにも適用されます。
私はすでにソースコードを開いているので:-) ...
close()
メソッドは、基になるReadable
がCloseable
インターフェイスも実装しているかどうかを確認し、実装している場合はそれを閉じます。あなたの状況では、これは後で閉じられるため、これは問題ではないと言っています。
ただし、close()
メソッドは、Scanner
(および基礎となるReadable
)が閉じていることを示す内部フラグも設定します。パブリックメソッドの多くは、最初にScanner
が閉じられているかどうかを確認します。そのため、ここでの危険性は、基礎となるReadable
が閉じられている可能性がありますが、Scanner
をさらに呼び出しても、すぐにIllegalStateException
がスローされず、代わりに他の彼らが進む方法。
問題のScanner
インスタンスへのハンドルが他にないことを確認でき、それ以上のメソッドを呼び出そうとしない場合は、大丈夫です。
close()
メソッドもReadable
への参照をnullにするため、これが起こらない場合は、Scanner
はすぐにガベージコレクションされません。 close()
を呼び出しました。
可能であれば、Scanner.close()
を呼び出します。
Scanner
も閉じる必要があり、さらに作業を進めるために、基になるストリームを開いたままにしておく必要がありました。私がやったのは、BufferedInputStream
を拡張し、close()
メソッドを空のボディでオーバーライドするクラスを作成することです。このクラスは、Scanner
のコンストラクターに入力しました。これにより、ストリームを閉じずにscanner.close()
を呼び出すことができます。ただし、元のBufferedInputStream
への参照を保持する必要がありますが、それは明らかです。
まあ、Caller and Readerクラスがあれば。呼び出し元は、Readerの実装について知る必要はありません。読者の次の方法では:
while scanner has object
read them ( one object per method's call)
when objects are done
close the reader.
これは一種のイテレータパターンです。