ひだまりソケットは壊れない

ソフトウェア開発に関する話を書きます。 最近は主に Android アプリ、Windows アプリ (UWP アプリ)、Java 関係です。

まじめなことを書くつもりでやっています。 適当なことは 「一角獣は夜に啼く」 に書いています。

Java でファイルの中身を読み込む方法 (Java SE 7 版)

なんとなくネットサーフィン (死語) してたら次の記事を見つけました。 確かに Java のファイル読み込みはいろいろややこしいですよね。

Java ファイル 読み込み」 とかで検索しても FileInputStreamInputStreamReader でラップしてさらに BufferedReader でラップする例が出てたりして、Java を使い始めたころの私も混乱させられました。

昔はこういった方法が当たり前でしたが、今ではもっと簡単になっています *1Java SE 7 で導入された FilesPath といった便利なクラスを使うことで、ファイル読み込みの処理を Java SE 6 以前より簡単に記述できるようになりました。

ファイルの中身を一気に読み込む

例えば、指定のパスのファイルの中身をバイト列として全部読み込むために Files.readAllBytes(Path path) メソッドを使用できます。 文字列として扱いたい場合は、String(byte bytes, Charset charset) コンストラクタ に、文字エンコーディングととも *2 に渡せばいいですね。

/* 必要な `import` 文
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
*/

// 指定のファイル URL のファイルをバイト列として読み込む
byte[] fileContentBytes = Files.readAllBytes(Paths.get("target_file_url"));
// 読み込んだバイト列を UTF-8 でデコードして文字列にする
String fileContentStr = new String(fileContentBytes, StandardCharsets.UTF_8);

ちなみに上の例では例外処理をしていませんが、チェック例外として IOException が発生するので、キャッチして終了するなり throws 句に書いておくなり適切に処理する必要があります。

ファイルの中身を読むための BufferedReader を生成する

ファイルの中身を指定の文字エンコーディングでデコードして、バッファリングしながら読み込もうと思ったら、冒頭でも書いたように FileInputStreamInputStreamReader でラップして *3 さらに BufferedReader でラップするというのが一般的でした。 次のようなコードです。

FileInputStream fis   = new FileInputStream("target_file_path");
InputStreamReader isr = new InputStreamReader(fis)
BufferedReader br     = new BufferedReader(isr);

BufferedReader オブジェクトを準備するのにどんだけインスタンス化するんだって話ですよね。 Files#newBufferedReader(Path, Charset) メソッド を使えば、もう少し簡単にファイルの中身を読むための BufferedReader を準備できます。

/* 必要な `import` 文
import java.io.BufferedReader;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Paths;
*/

try (BufferedReader br2 = Files.newBufferedReader(Paths.get("target_file_url"), StandardCharsets.UTF_8)) {
    for (String line; (line = br2.readLine()) != null;) {
        // line に対する処理
    }
}

例によって上のコードには書いていませんが IOException を適切に扱う必要があります。 あと上の例では close を自動で行ってくれるように try-with-resources 文を使っています。 try-with-resources 文については次の記事が参考になります。

その他いろいろ

Files クラスには他にもいろいろと便利なメソッドが定義されているので調べてみると良さそうです。 この記事では読み込みの話ばかり書きましたが、もちろん書き込みを含めたファイル入出力周りや、その他ファイルシステム関係のあれこれがあります。

*1:とはいえこれらの手法がどういう意味を持っているのかを理解するのは今でも重要です。

*2:デフォルト文字エンコーディングを使用させたい場合は文字エンコーディングを指定せずとも良いですが。

*3:文字エンコーディングを明示的に指定しないならば単に FileReader を使っても良いのですが、明示的に文字エンコーディングを指定するならば FileReader は使えません。