This article is participating in “Java Theme Month – Java Debug Notes Event”, see < Event link > for more details.

Question: Use try-finally blocks to prevent StackOverflowError problems

Take a look at the following code in two ways:

public static void foo(a) {
    try {
        foo();
    } finally{ foo(); }}public static void bar(a) {
    bar();
}
Copy the code

Bar runs cause StackOverflowError, but Foo does not. The program appears to run indefinitely.

What’s the problem?

Answer 1:

It won’t run forever. Each stack overflow causes code to move to a finally block. The problem is that it will take a very, very long time. The chronological order is O (2 ^ N), where N is the maximum stack depth.

For example, the maximum depth N=5

foo() calls
    foo(a) calls
       foo(a) calls
           foo(a) calls
              foo(a) which fails to call foo(a)
           finally calls
              foo(a) which fails to call foo(a)
       finally
           foo(a) calls
              foo(a) which fails to call foo(a)
           finally calls
              foo(a) which fails to call foo(a)
    finally calls
       foo(a) calls
           foo(a) calls
              foo(a) which fails to call foo(a)
           finally calls
              foo(a) which fails to call foo(a)
       finally
           foo(a) calls
              foo(a) which fails to call foo(a)
           finally calls
              foo(a) which fails to call foo(a)
finally calls
    foo(a) calls
       foo(a) calls
           foo(a) calls
              foo(a) which fails to call foo(a)
           finally calls
              foo(a) which fails to call foo(a)
       finally
           foo(a) calls
              foo(a) which fails to call foo(a)
           finally calls
              foo(a) which fails to call foo(a)
    finally calls
       foo(a) calls
           foo(a) calls
              foo(a) which fails to call foo(a)
           finally calls
              foo(a) which fails to call foo(a)
       finally
           foo(a) calls
              foo(a) which fails to call foo(a)
           finally calls
              foo(a) which fails to call foo(a)
Copy the code

It takes twice as long to get each level into a finally block, and the stack depth can be 10,000 or more. If you could make 10,000,000 calls per second, it would take 10 ^ 3003 seconds, even longer than the universe has existed.

The article translated from Stack Overflow: stackoverflow.com/questions/1…