ループが終わらない・空回りする原因
カウンタ更新の忘れ、更新方向の誤り、forの直後のセミコロンという3パターンを扱います。
なぜエラーが出ないのか
出力: 0 が無限に続く
(エラーなし)- javacは何も報告しません。文法として正しいためです
出力: 0 が無限に続く- 実際の挙動 — 期待した結果と食い違っている箇所
見つけ方- エラーが出ないので、出力を目で確かめるしかありません。この種の誤りが最も発見が遅れます
このエラーが出る典型パターン
パターン1
1 public class Main { 2 public static void main(String[] args) { 3 int i = 0; 4 while (i < 3) { 5 System.out.println(i); 6 ^ 7 } 8 } 9 }
出力: 0 が無限に続く(プロセスが終わりません)
whileは条件を変える処理を自分で書きます。カウンタの更新を忘れると止まりません。
直し方: (空) を i++; にします。
広告
広告スロット(未設定)
パターン2
1 public class Main { 2 public static void main(String[] args) { 3 for (int i = 0; i < 3; i-- ) { ^ 4 System.out.println(i); 5 } 6 } 7 }
出力: 0 -1 -2 ... が無限に続く(プロセスが終わりません)
更新式が条件を満たす方向に動いていないと終わりません。増加か減少かを条件と合わせます。
直し方: -- を ++ にします。
パターン3
1 public class Main { 2 public static void main(String[] args) { 3 int count = 0; 4 for (int i = 0; i < 3; i++); ^ 5 count++; 6 System.out.println(count); 7 } 8 }
出力: 1期待: 3 (コンパイルは通っています)
forの直後のセミコロンは「本体が空」を意味します。ループが空回りし、次の行は1回だけ実行されます。
直し方: ; を (空) にします。
パターン4
1 public class Main { 2 public static void main(String[] args) { 3 int i = 0; 4 do { 5 System.out.println(i); 6 ^ 7 } while (i < 3); 8 } 9 }
出力: 0 が無限に続く(プロセスが終わりません)
do-whileも条件を変える処理は自分で書く必要があります。カウンタの更新を忘れると止まりません。
直し方: (空) を i++; にします。
パターン5
1 public class Main { 2 public static void main(String[] args) { 3 int i = 0; 4 boolean cont = true; 5 while (cont = true) { ^ 6 System.out.println(i); 7 i++; 8 if (i >= 3) cont = false; 9 } 10 } 11 }
出力: 0 1 2 3 4 ... が無限に続く(プロセスが終わりません)
whileの条件で = を書くと、毎回contにtrueを代入してしまいます。ループ内でfalseにしても次の判定で上書きされ、条件は常にtrueのままです。
直し方: = を == にします。
よくある誤解
forの直後のセミコロンはエラーになりません。文法上は正しい「空の本体」だからです。
実務での勘所
無限ループはコンパイルエラーにも警告にもならないことがほとんどです。停止するかどうかを一般的に判定することは理論的に不可能(停止性問題)なので、javacやIDEがこれを検出して教えてくれることは期待できません。一方でwhile (true) { ... break; }のように、意図的に無限ループとbreakを組み合わせる書き方は、サーバーのリクエスト待ちやゲームのメインループなどで実務でも普通に使われる正当なパターンです。「無限ループ=バグ」ではなく、終了条件を書き忘れたものだけがバグです。