コース一覧
    Java中級:例外処理とファイル入出力
    try-with-resources

    Java中級:例外処理とファイル入出力

    例外処理とファイル入出力を学び、失敗に対応しながらデータを読み書きするプログラムを作れるようにします。

    1
    例外処理
    01. try-catch で例外をつかむ5分
    02. 複数の catch ブロック5分
    03. throws と例外の伝播5分
    04. 独自の例外を作る5分
    05. try-with-resources5分
    06. finally ブロック5分
    07. 例外処理 まとめクイズ5分
    2
    ファイル I/O
    01. Files でファイルに書き込む5分
    02. ファイルを行単位で読む5分
    03. Path でファイルパスを扱う5分
    04. BufferedReader と Stream API5分
    05. ファイルの存在確認と削除5分
    06. ファイル I/O まとめクイズ5分

    try-with-resources

    close() の行に、たどり着けないことがある

    ファイルを開いて 1 行読むだけのコードです。最後にきちんと close() も書いてあります。

    Java

    BufferedReader reader = new BufferedReader(new FileReader(path));
    String line = reader.readLine();
    System.out.println(line.trim());
    reader.close();

    ところが空のファイルを渡すと readLine() が null を返し、line.trim() で NullPointerException が飛びます。処理はその場で打ち切られるので、最後の reader.close() は実行されません。ファイルは開いたままです。

    ここが厄介なのは、すぐには何も壊れないことです。ガベージコレクタが片付けてくれるのは Java のヒープの中だけで、OS が持っているファイルハンドルやソケット、データベース接続は close() を呼ぶまで戻ってきません。同じ処理を数千回繰り返したあと、Too many open files でサーバーが止まって初めて気づきます。

    finally に移せば例外が出ても呼ばれますが、本筋ではないコードのほうが長くなります。

    Java

    BufferedReader reader = null;
    try {
        reader = new BufferedReader(new FileReader(path));
        System.out.println(reader.readLine().trim());
    } finally {
        if (reader != null) {
            reader.close();
        }
    }

    try のかっこに書くと、勝手に閉じてくれる

    Java 7 以降は、try の直後のかっこの中でリソースを宣言できます。

    Java

    try (BufferedReader reader = new BufferedReader(new FileReader(path))) {
        System.out.println(reader.readLine().trim());
    }

    これだけです。かっこの中で宣言した変数は try ブロックの中だけで有効で、ブロックを抜けるときに close() が自動で呼ばれます。正常に抜けたときも、途中で例外が飛んだときも同じです。閉じ忘れが構文レベルで起こらなくなったわけです。

    かっこの中には、セミコロンで区切って複数のリソースを並べられます。閉じられる順番は宣言と逆順です。あとから開いたものが先に閉じるので、接続の上に文を載せるような依存関係があっても、自然な順序で片付きます。

    かっこに書けるのは AutoCloseable だけ

    try のかっこに置けるのは、java.lang.AutoCloseable を実装した型に限られます。中身は close() メソッド 1 つだけの、とても小さなインタフェースです。

    BufferedReader InputStream Scanner Connection といった標準ライブラリのリソース系クラスは、すべて実装済みです。自分で書いたクラスも implements AutoCloseable と宣言して close() を用意すれば、同じように置けます。実装を忘れると required type that implements AutoCloseable というコンパイルエラーで止まります。

    よくある間違い

    いちばん多い勘違いは、「これを使えば例外処理そのものが要らなくなる」というものです。自動になるのは close() の呼び出しだけで、ブロックの中で起きた例外はそのまま外へ飛んでいきます。受け止めたいなら catch を書き足してください。かっこと catch は併用できます。

    もう 1 つ、close() の中に重い処理や独自の例外を仕込むのも避けましょう。後始末は静かに終わるのが理想です。

    要件

    1. Solution の中に static class Resource implements AutoCloseable を定義し、close() メソッドを実装すること
    2. Resource のコンストラクタで "opened"、use() で "-used"、close() で "-closed" を StringBuilder に append すること
    3. try-with-resources 構文 (try (Resource r = new Resource(log)) { ... }) を使い、finally で明示的に close() を呼ばないこと

    ヒント

    `static class Resource implements AutoCloseable { ... }` を `Solution` の中に書くと、`Solution.dummyClose()` から `new Resource(log)` で生成できます

    `close()` メソッドは `public void close()` のシグネチャで定義します。`throws Exception` は今回は不要です

    `try (Resource r = new Resource(log)) { r.use(); }` と書けば、ブロックを抜けるときに `r.close()` が自動で呼ばれます。`return log.toString()` は `try` の外で呼びましょう

    生田 陸人
    監修生田 陸人
    ゆめさくエンジニア / 現役ソフトウェアエンジニア監修者プロフィールを見る →
    編集 ゆめさく編集部·公開 2026/05/19·更新 2026/08/26

    関連レッスン

    • finally ブロック

      Java の `try` 文で必ず実行される `finally` ブロックの役割をリソース解放や後始末の観点から学び、整数除算の結果を `,end` 付きで返すメソッドを実装してみよう。

    • 例外処理 まとめクイズ

      例外処理 (try-catch / 複数 catch / throws / カスタム例外 / try-with-resources / finally) の総まとめ。検査例外と非検査例外、catch の順序、finally で return など実務頻出のポイントを 4 択クイズで確認する。

    • Files でファイルに書き込む

      Java の標準ライブラリ `java.nio.file.Files` を使って、ファイルへの書き込みと読み込みをわずか数行で実現する方法を学ぼう。

    このレッスンに出てくる用語

    意味があいまいなまま進んだ語は、ここから読み直せます。

    • 処理計算や代入を表す長方形
    • ヒープ親が子より常に大きい(最大ヒープ)または小さい(最小ヒープ)木構造。
    • データベースデータを構造化して保存する仕組み
    • サーバークライアント(ブラウザなど)がリクエストを送り、サーバーがレスポンスを返す。
    • 変数データに名前をつけて参照する仕組み
    • ロック「他の人触らないでね」と DB に予約する
    • メソッドクラスに属する関数
    • 標準ライブラリPythonに同梱の公式モジュール群
    main.java
    エディタを読み込んでいます

    メモ

    try-with-resources

    ⌘S で保存