How to Fix Unreachable Statement Errors in Java

How to Fix Unreachable Statement Errors in Java
Table of Contents

You hit compile, confident your code is solid. Then you see it: unreachable statement error. You stare at the line - it looks perfectly fine. What's going on?

This is one of Java's most common compile-time errors, and it happens when the compiler detects code that can never execute. As a compiled language, Java catches these issues before your code ever runs, preventing bugs from reaching production [2]. Understanding why statements become unreachable will save you debugging time and help you write cleaner, more intentional code.

Statements are the building blocks of Java programs - they tell your code what to do. Java has three main types: expression statements, declaration statements, and control-flow statements [1]. The unreachable statement error occurs when control-flow goes wrong.

 

What Causes the Unreachable Statement Error?

The Java compiler analyzes your code's execution paths. It checks whether every statement can be reached from the beginning of a method, constructor, or initializer. If the compiler finds a statement with no possible execution path leading to it, it raises the unreachable statement error [3].

Think of it like this: if your code takes an exit before reaching a statement, that statement can never run. The compiler won't let you keep dead code around.

 

Unreachable Statement Error Examples

After Branching Control-Flow Statements

The break, continue, and return statements redirect your program's execution flow. When you use one of these branching statements, you're telling Java to jump somewhere else immediately [4]. Any code that comes right after them? Unreachable.

After break

Here's a common mistake when searching through an array:

(a)

package rollbar;
public class UnreachableStatementBreak {
public static void main(String... args) {
int[] arrayOfInts = {35, 78, 3, 589, 12, 1024, 135};
   int searchFor = 12;

   for (int integer : arrayOfInts) {
       if (integer == searchFor) {
           break;
           System.out.println("Found " + searchFor);
       }
   }
}
}
UnreachableStatementBreak.java:12: error: unreachable statement
        System.out.println("Found " + searchFor);
        ^

The break statement on line 11 immediately exits the loop. The print statement on line 12 never gets a chance to run. To fix this, track whether you found the value, then print after the loop completes:

(b)

package rollbar;
public class UnreachableStatementBreak {
public static void main(String... args) {
int[] arrayOfInts = {35, 78, 3, 589, 12, 1024, 135};
   int searchFor = 12;
   boolean found = false;

   for (int integer : arrayOfInts) {
       if (integer == searchFor) {
           found = true;
           break;               
       }
   }

   if (found) {
       System.out.println("Found " + searchFor);
   }
}
}
Found 12

Figure 1: Unreachable statement after a break statement (a) error and (b) resolution

After continue

The same principle applies to continue. When you skip to the next loop iteration, anything after the continue statement is left behind:

(a)

package rollbar;
public class UnreachableStatementContinue {
public static void main(String... args) {
int[] arrayOfInts = {35, 78, 3, 589, 12, 1024, 135};
   int oddSum = 0;

   for (int integer : arrayOfInts) {
       if (integer % 2 == 0) {
           continue;
           System.out.println("Skipping " + integer + " because it's even");
       }
       oddSum += integer;
   }
   System.out.println("\nThe sum of the odd numbers in the array is: " + oddSum);
}
}
UnreachableStatementContinue.java:12: error: unreachable statement
        System.out.println("Skipping " + integer + " because it's even");
        ^

The continue on line 11 jumps to the next iteration immediately. Line 12 never executes. The fix? Move the print statement before the continue:

(b)

package rollbar;
public class UnreachableStatementContinue {
public static void main(String... args) {
int[] arrayOfInts = {35, 78, 3, 589, 12, 1024, 135};
   int oddSum = 0;

   for (int integer : arrayOfInts) {
       if (integer % 2 == 0) {
           System.out.println("Skipping " + integer + " because it's even");
           continue;
       }
       oddSum += integer;
   }
   System.out.println("\nThe sum of the odd numbers in the array is: " + oddSum);
}
}
Skipping 78 because it's even
Skipping 12 because it's even
Skipping 1024 because it's even

The sum of the odd numbers in the array is: 762

Figure 2: Unreachable statement after a continue statement (a) error and (b) resolution

 

After return

When a method returns, it exits immediately. Nothing else in that method runs:

(a)

package rollbar;
public class UnreachableStatementReturn {
static int factorial(int n) {
int f = 1;
for (int i = 1; i <= n; i++) {
f *= i;
}
return f;
System.out.println("Factorial of " + n + " is " + f);
}
public static void main(String... args) {
factorial(10);
}
}
UnreachableStatementReturn.java:11: error: unreachable statement
        System.out.println("Factorial of " + n + " is " + f);
        ^

Line 10's return exits the method. Line 11 is dead code. If you want to print the result, do it from the calling code instead:

(b)

package rollbar;
public class UnreachableStatementReturn {
static int factorial(int n) {
int f = 1;
for (int i = 1; i <= n; i++) {
f *= i;
}
return f;
}
public static void main(String... args) {
int n = 10;
System.out.println("Factorial of " + n + " is " + factorial(n));
}
}
Factorial of 10 is 3628800

Figure 3: Unreachable statement after a return statement (a) error and (b) resolution

 

After a throw Statement

When your code throws an exception, it immediately jumps to the nearest exception handler (usually a catch block) [5]. This means any statement after a throw is unreachable:

(a)

package rollbar;
public class UnreachableStatementException {
public static void main(String... args) {
try {
throw new Exception("Custom exception");
System.out.println("An exception was thrown");
} catch (Exception e) {
System.out.println(e.getMessage() + " was caught");
}
}
}
UnreachableStatementException.java:7: error: unreachable statement
        System.out.println("An exception was thrown");
        ^

Line 6 throws the exception, jumping straight to the catch block. Line 7 never executes. Move any necessary code to the catch block where it can actually run:

(b)

package rollbar;
public class UnreachableStatementException {
public static void main(String... args) {
try {
throw new Exception("Custom exception");
} catch (Exception e) {
System.out.println("An exception was thrown");
System.out.println(e.getMessage() + " was caught");
}
}
}
An exception was thrown
Custom exception was caught

Figure 4: Unreachable statement after a throw statement (a) error and (b) resolution

 

Inside a while Loop with a Constant False Condition

Here's a less obvious case. If a while loop's condition is always false, the loop body never executes:

package rollbar;
public class UnreachableStatementWhile {
public static void main(String... args) {
final boolean start = false;
   while (start) {
       System.out.println("Unreachable Statement");
   }
}
}
UnreachableStatementWhile.java:7: error: unreachable statement
        while (start){
                     ^

Figure 5: Unreachable while statement

The variable start is final and set to false. The compiler knows it can never be true, so the loop body on line 8 is unreachable. While this example is obvious, similar issues can occur with more complex constant expressions.

 

Summary

The unreachable statement error is Java's way of keeping your code clean. It catches dead code before it becomes a production problem. Remember the core principle: if your code jumps away (via break, continue, return, or throw), nothing after it will run.

To avoid this error:

  • Place any necessary code before branching statements
  • Move post-return logic to the calling code
  • Handle exception-related messages in catch blocks
  • Check that loop conditions can actually be met

Managing Java Errors in Production

While compile-time errors like unreachable statements are caught before deployment, runtime errors are a different story. Tracking and managing errors in production requires robust monitoring.

Track, Analyze and Manage Errors With Rollbar

Rollbar in action

Managing errors and exceptions in your code is challenging. It can make deploying production code an unnerving experience. Being able to track, analyze, and manage errors in real-time can help you to proceed with more confidence. Rollbar automates error monitoring and triaging, making fixing Java errors easier than ever. Sign Up Today!


References

[1] Oracle, 2021. Expressions, Statements, and Blocks (The Java™ Tutorials > Learning the Java Language > Language Basics). Oracle and/or its affiliates. [Online]. Available: https://docs.oracle.com/javase/tutorial/java/nutsandbolts/expressions.html. [Accessed Nov. 10, 2021].

[2] Rollbar, 2021. Illegal Start of Expression: A Java Compile-time Errors Primer. Rollbar Editorial Team. [Online]. Available: https://rollbar.com/blog/how-to-fix-illegal-start-of-expression-in-java/. [Accessed Nov. 10, 2021].

[3] Oracle, 2021. The Java® Language Specification. Chapter 14. Blocks, Statements, and Patterns. Unreachable Statements. Oracle and/or its affiliates. [Online]. Available: https://docs.oracle.com/javase/specs/jls/se17/html/jls-14.html#jls-14.22. [Accessed Nov. 10, 2021].

[4] Oracle, 2021. Branching Statements (The Java™ Tutorials > Learning the Java Language > Language Basics). Oracle and/or its affiliates. [Online]. Available: https://docs.oracle.com/javase/tutorial/java/nutsandbolts/branch.html. [Accessed Nov. 10, 2021].

[5] Oracle, 2021. How to Throw Exceptions (The Java™ Tutorials > Essential Java Classes > Exceptions). Oracle and/or its affiliates. [Online]. Available: https://docs.oracle.com/javase/tutorial/essential/exceptions/throwing.html. [Accessed Nov. 10, 2021].

Build with confidence. Release with clarity.

Rollbar helps you track what breaks, understand why, and improve what comes next.

5K free events per month, forever
14-day full feature trial
Easy and quick installation
Get started in minutes

Plans starting at $0. Take off with our 14-day full feature Free Trial.