java.ioパッケージはJ2SEで、データストリーム、直列化、およびファイルシステムによるシステム入出力用として提供されています。このパッケージに含まれる多くのクラスの中で、特に利用場面が多いのがReaderクラスをスーパークラスとする、文字ストリームを読み込むためのクラス群です。
しかし、このReader系クラスはいくつもあり、使い分けが悩ましいところです。効率の悪い使い方をすると、ただでさえ遅い入出力処理をなおさらボトルネックにしてしまったり、読みづらいプログラムになってしまいます。
Reader系クラスの種類
各クラスの目的と特徴をまとめると、下表のようになります。
クラス名 | 目的・概略 | 特徴 | |
---|---|---|---|
Reader | 文字ストリームを読み込む | 抽象クラスだが、単一文字を読むread()メソッドなどは実装されている | |
StringReader | ソースが文字列の文字ストリーム | Readerを直接継承。必要最小限の機能を備える | |
PipedReader | パイプによる文字入力ストリーム | Readerを直接継承。パイプによるストリームから、次の文字を読み込んだり、パイプによるリーダを、パイプによるライタに接続させられる | |
InputStreamReader | バイトストリームから文字ストリームへの橋渡し | Readerを直接継承。バイトデータを読み込んで、指定されたcharsetを使用して(または、プラットフォームのデフォルトの文字エンコーディングで)文字に変換する | |
FileReader | 文字ファイルからの読み込み | InputStreamReaderをスーパークラスとする簡易クラス。文字エンコーディングとバイトバッファのサイズはデフォルトで適切な設定がされていることを仮定している | |
FilterReader | フィルタ処理された文字列ストリームを読み込む | Readerを直接継承する抽象クラスだが、定義されているメソッドはすべて実装されている | |
PushbackReader | 文字をストリームにプッシュバックできる文字ストリームリーダ | FilterReaderをスーパークラスとする具象クラス。指定されたサイズのプッシュバックバッファを持つプッシュバックリーダを作成 | |
CharArrayReader | 文字入力ストリームとして使用する文字バッファを実装する | Readerを直接継承。文字バッファはchar型の配列。現在のバッファの位置やバッファの最後のインデックスを示すフィールドを持つ | |
BufferedReader | 文字、配列、行をバッファリングすることによって、文字型入力ストリームからテキストを効率よく読み込む | Readerを直接継承。ほかの効率の良くないReader系クラスをラップすることで、バッファリングによる効率向上を与える | |
LineNumberReader | 行番号を追跡して管理する、バッファリングされた文字入力ストリーム | BufferedReaderをスーパークラスとするので効率が高い。現在の行番号を設定するメソッドと、現在の行番号を取得するメソッドが定義されている |
この中でも特に、BufferedReaderクラスの活用がキーになります。バッファリングせずにread()、readLine()を使うと、呼び出しごとにファイルからバイトを読み込み、文字型に変換し、そのたびに復帰するので、非常に効率が悪くなります。
例えば、ファイル「a.txt」からの入力をバッファするために、下記のように記述することが推奨されています。
BufferedReader in = new BufferedReader(new FileReader("a.txt"));
バッファリング+行番号処理には、LineNumberReaderが便利
では、使い分けの一例を挙げましょう。
BufferedReaderクラスに比べると活用の度合いが小さいようですが、BufferedReaderクラスのサブクラスであるLineNumberReaderはなかなか便利なクラスです。
現在の行番号を設定するsetLineNumber(int)メソッドと、現在の行番号を取得するgetLineNumber()メソッドを持ち、しかも、BufferedReaderクラスのサブクラスですから、読み込みの効率も高いのがポイントです。
一例として、テキストファイルを行読みして、空行でなければ、その行の番号と内容を出力するプログラムを作成すると、以下のようになります。
なお、setLineNumber(int)メソッドは、ストリーム内の現在位置を実際に変更するのではなく、getLineNumber()から返される値を変更するだけですので、ご注意ください。
Copyright © ITmedia, Inc. All Rights Reserved.