ストリーム

Javaにおけるデータ入出力の考え方

オブジェクト指向言語であるJavaでは、データの入出力にもクラスを使います。 データの流れをクラスInputStream/OutputStreamのインスタンスとして扱い、 それらに対して読み書きをするのにクラスInputStreamReader/OutputStreamWriterを用います。

InputStream and InputStreamReader

上記の図は入力を行う際の概念図ですが、実際にデータ入力を行う際には、 対象とするデータの種類やデータのある場所によって、行うべき処理内容が異なってきます。 例えば、ローカルのディスクに存在するファイルからの読み込みと、 ネットワークを介したサーバの応答の受信では、明らかに処理が異なります。

Javaではオブジェクト指向の特徴を生かし、 入力データ全般に成り立つ性質をクラスInputStreamに持たせ、 それを継承する形で様々な種類の入力データに対応するよう、 多くのクラスが用意されています。

ファイル入力

入力用のデータがファイルの場合、データはクラスInputStreamを継承している クラスFileInputStreamのオブジェクトとして扱います。 また、データがファイルの場合には、ディスクからデータを読み込む際にある程度の大きさのデータをまとめて読み込んで効率を上げるバッファリングと呼ばれる処理が必要です。 そのバッファリングの機能を持ったReaderであるBufferedReaderを、InputStreamReaderにかぶせて使います(これを「ラップする」と言います)。

FileInputStream and BufferedReader

BufferedReaderを使って読み込むまでの手続きは以下のようになります。

// まずファイル名を与えてFileInputStreamのインスタンスisを生成
InputStream is = new FileInputStream("foo.txt");
// 次にisを読み込むInputStreamReaderのインスタンスisrを生成
InputStreamReader isr = new InputStreamReader(is, "UTF-8");
// さらにisrをラップするBufferedReaderのインスタンスrを生成
BufferedReader r = new BufferedReader(isr);

この後に続く読み込みの処理では、isやisrにメッセージを送る必要はなく、 rに読み込みのメッセージを送ります。

// 1行読み込んで文字列lineに代入
String line = r.readLine();

isやisrはあとで参照することがないのですから、 次のようにnewで生成したインスタンスを直接引数として与える書き方が可能です。

BufferedReader r = new BufferedReader(
    new InputStreamReader(
        new FileInputStream(filename ), encoding ));

InputStreamReader

InputStreamReaderは、InputStreamの様々なencoding(文字コード)に対応できる Reader です。

コンストラクタ

読み込む先である InputStream と、encoding(日本語なら漢字コード)を指定します。

encoding

日本語の文字を表現するコードとして代表的なものは以下の通りです。

"JISAutoDetect"と指定すると、"EUC_JP", "SJIS", "ISO2022JP"の場合に自動判別されますが、 間違いもあります。半角カナを含む SJIS と EUC_JP との自動判別は厳密には不可能です。 特定のフォームからの入力など、 encoding があらかじめわかっている場合には自動判別を避けたほうが安全です。

使用例

ファイルの場合

InputStream iStream = new FileInputStream("foo.txt");
InputStreamReader r = new InputStreamReader(iStream, "UTF-8");
InputStreamReader r = new InputStreamReader(
      new FileInputStream("foo.txt"), "EUC_JP"));

URLConnectionの場合

URL url = URL("http://java.sun.com/");
URLConnection urlConnection = url.openConnection();
urlConnection.connect();
InputStreamReader r = new InputStreamReader(
    urlConnection.getInputStream(), "UTF-8");

BufferedReader

  BufferedReaderは、バッファリングをする機能を持った Reader です。

  バッファリングとは、データを読み込む際にある程度の大きさのデータをまとめて 読み込んでメモリに蓄えてしまい、プログラムには要求しただけの量を読んだように 見せることによって、速度を上げる技術です。

  コンストラクタは BufferedReader(InputStreamReader isr) です。