考虑到这段代码,我能绝对确定finally块总是执行的吗,不管something()是什么?

try {  
    something();  
    return success;  
}  
catch (Exception e) {   
    return failure;  
}  
finally {  
    System.out.println("I don't know if this will get printed out");
}

当前回答

即使在try块中放入return语句,也始终执行finally块。finally块将在return语句之前执行。

其他回答

除了最后替换try块中的返回之外,异常也是如此。引发异常的finally块将替换try块中引发的返回或异常。

简而言之,在官方Java文档(单击此处)中-

如果JVM在执行try或catch代码时退出,则finally块可能不执行。同样,如果线程执行try-or-catch代码被中断或终止,finally块可能即使应用程序作为一个整体继续,也不会执行。

答案很简单:是。

输入:

try{
    int divideByZeroException = 5 / 0;
} catch (Exception e){
    System.out.println("catch");
    return;    // also tried with break; in switch-case, got same output
} finally {
    System.out.println("finally");
}

输出:

catch
finally

如果在嵌套的finally块中引发异常,finally也可以提前退出。编译器会警告你finally块没有正常完成,或者给出一个错误,说明你有无法访问的代码。仅当抛出不在条件语句后面或循环内部时,才会显示不可访问代码的错误。

try{
}finally{
   try{
   }finally{
      //if(someCondition) --> no error because of unreachable code
      throw new RunTimeException();
   }
   int a = 5;//unreachable code
}

不总是这样

Java语言规范描述了try-catch finally和try-catch块在14.20.2在任何地方,它都不会指定始终执行finally块。但对于try-catch-finally和try-finally块完成的所有情况,它确实指定在完成之前必须执行finally。

try {
  CODE inside the try block
}
finally {
  FIN code inside finally block
}
NEXT code executed after the try-finally block (may be in a different method).

JLS不保证在CODE之后执行FIN。JLS保证,如果执行CODE和NEXT,则FIN将始终在CODE之后和NEXT之前执行。

为什么JLS不能保证finally块总是在try块之后执行?因为这是不可能的。在完成try块之后但在执行finally块之前,JVM不太可能被中止(终止、崩溃、断电)。JLS无法避免这种情况。

因此,任何软件的正常行为都取决于最终块,总是在其尝试块完成后执行。

try块中的返回指令与此问题无关。如果执行在try-catch finally之后到达代码,则可以保证finally块之前已经执行过,无论是否在try块内有返回指令。