【Java学習|実務向け】Javaの制御フローを極める:Labeled continueと現代的な言語機能の活用術

導入

Javaでのプログラミングにおいて、多重ループ(入れ子になったfor文やwhile文)から抜け出したり、特定の処理をスキップしたりするケースは頻繁に発生します。通常のbreakやcontinueは「直近のループ」にしか影響しませんが、Labeled continue(ラベル付きcontinue)を活用することで、外側のループを直接制御し、可読性と効率を両立させることができます。本稿では、レガシーな制御フローから、モダンなJava(Java 17以降)の機能を組み合わせた効率的なコーディング手法を解説します。

基礎知識

Labeled continueとは、ループ文の直前に「ラベル名:」を付与し、内側のループからそのラベルを指定してcontinueを行う仕組みです。

  • 通常のcontinue: 直近のループの次の反復へ移行。
  • Labeled continue: 指定したラベルの外側ループの次の反復へ移行。

同様の概念でbreakを使うことも可能ですが、continueと組み合わせることで「特定の条件を満たした場合だけ、外側のループまで戻って次の要素を処理する」といった複雑なロジックを簡潔に表現できます。また、Java 14以降で導入されたswitch expressionsyieldsealed classesといった現代的な制御構文を組み合わせることで、エラーの少ない堅牢なコードが書けます。

実装/解決策

多重ループの中で「条件を満たしたとき、現在の内側ループを中断し、外側のループの次のインデックスへ進みたい」という場合、フラグ変数(boolean)を多用しがちです。しかし、フラグ管理はバグの温床となります。ここでLabeled continueを使用すれば、フラグなしで直感的な制御が可能です。

サンプルプログラム

以下のコードは、二次元配列から特定の条件に合致する要素を探し、見つかった場合は外側ループの次の要素へスキップする例です。

public class LoopControlExample {
    public static void main(String[] args) {
        int[][] matrix = {
            {1, 2, 3},
            {4, 5, 6},
            {7, 8, 9}
        };

        // 外側のループにラベルを付与
        outerLoop:
        for (int i = 0; i < matrix.length; i++) {
            for (int j = 0; j < matrix[i].length; j++) {
                int value = matrix[i][j];

                // 5という数値が見つかったら、外側ループの次の行へジャンプ
                if (value == 5) {
                    System.out.println("5を発見!行をスキップします。");
                    continue outerLoop; 
                }
                
                System.out.println("処理中: " + value);
            }
        }
    }
}

応用・注意点

1. 過度な利用の回避: Labeled continueは強力ですが、多用しすぎると「スパゲッティコード」の原因となります。コードが複雑になりすぎる場合は、メソッドを分割してreturnで抜ける設計を検討してください。
2. モダン機能との併用: 現代的なJava開発では、複雑なループを避けるためにStream APIを活用するのが推奨されます。しかし、パフォーマンスが極めて重要な低レイヤー処理や、特定のアルゴリズム実装ではLabeled continueが最適解となることもあります。
3. Sealed Classesとの組み合わせ: switch expressionsで処理分岐を行う際、sealed classesを使用すると、網羅性が保証されます。ループ処理の結果をswitchで受け取り、yieldで値を返すような設計にすることで、より宣言的で安全なコードになります。

現場のシニアエンジニアとしては、単に「動くコード」ではなく、「後続のエンジニアが論理を追いやすいコード」を意識してください。ラベル命名には、そのループが何をしているのか(例: outerProcess, rowLoop)を明示的に記述するのがコツです。

コメント

タイトルとURLをコピーしました