Java finally語句到底是在return之前還是之後執行
看過網上關於Java中異常捕獲機制try…catch…finally塊中的finally語句是不是一定會被執行的討論也有很多。
首先明確一點,下面兩種情況finally肯定是不執行的:
1). return語句在try之前,還沒執行就返回了,當然不執行。
2). try語句中用了system.exit(0)強制退出JVM,暴力退出當然也不會執行。
先來看下面的代碼
package com.loongshaw;
public class TryReturnFinally {
public static void main(String[] args) {
System.out.println(test1());
}
public static int test1() {
int b = 1;
try {
System.out.println("try block");
return ++b;
}
catch (Exception e) {
b = 10;
System.out.println("catch block");
}
finally {
++b;
System.out.println("finally block");
}
System.out.println("last block");
return b;
}
}
如果你覺得其執行結果是3,那麽請你繼續看下去,中招了吧,哈哈。
先看看執行結果吧:
try block
finally block
2
- 1
- 2
- 3
可以看出,上面代碼的執行結果是2。常規想法其finally也執行了,try中也執行了,明明執行了兩個++b呢,咋回事呢?
這個時候,咱打斷點看看:
(1). 當程序執行到try中的return語句時,這時b還是1.
(2). 接著程序執行到finally語句時,執行了++b,b變為2.
(3). 這時,我們點擊try…return中的b,發現其值變為2.
以上結果說明了一點:return語句執行了,然後再執行了finally語句,但是return語句並沒有直接返回,而是待finally語句執行完了再返回。
通過下面這個測試用例加強理解:
package com.loongshaw;
public class TryReturnFinally {
public static void main(String[] args) {
System.out.println(test2());
}
public static String test2() {
try {
System.out.println("try block");
return test3();
}
catch (Exception e) {
System.out.println("catch block");
}
finally {
System.out.println("finally block");
}
System.out.println("last block");
return "last block";
}
public static String test3() {
System.out.println("return block");
return "output return block";
}
}
執行結果:
try block
return block
finally block
output return block
通過上述結果可以得出,在執行try語句中的return時,其test3()方法是被執行了的,其返回值保存在一個臨時變量中,然後去執行finally語句。
try {
System.out.println("try block");
return test3();
}
最後輸出存進臨時變量返回值。
output return block
- 1
可能大家會繼續說,如果finally和catch中有return,那是一種什麽情況:
(1) 首先看catch中有return
public static int test4() {
int b = 1;
try {
System.out.println("try block");
return b/0;
}
catch (Exception e) {
System.out.println("catch block");
return ++b;
}
finally {
b = b+ 10;
System.out.println("finally block");
}
}
結果
try block
catch block
finally block
2
可見,catch中的return與try一樣,finally都會執行,但是不影響try和catch中的return結果。
(2) 然後看finally中有return
public static int test5() {
int b = 1;
try {
System.out.println("try block");
return ++b;
}
catch (Exception e) {
++b;
System.out.println("catch block");
return b;
}
finally {
b = b+ 10;
System.out.println("finally block");
return b;
}
}
結果
try block
finally block
12
可見,finally中的return直接返回了,這與try和catch中的return是不同的。
大家可能發現test1()方法最後的return是沒有執行的,是不是。
public static int test1() {
...
System.out.println("last block");
return b;
...
}
通常情況是不會執行的,除非觸發了catch。下面是修改後的片段代碼:
public static int test1() {
int b = 1;
try {
b = b/0;
System.out.println("try block");
return ++b;
}
catch (Exception e) {
b = 10;
System.out.println("catch block");
}
finally {
b = b+ 10;
System.out.println("finally block");
}
System.out.println("last block");
return b;
}
執行結果:
catch block
finally block
last block
20
通過上述結果可以得出,在catch觸發時,最外層的return是會被執行的。
總結:
- finally語句在try和catch語句中的return執行後、返回前執行;
- 若finally語句中沒有return,則其執行結果不影響try和catch中已確定的返回值;
- 若finally語句中有return,則其執行後的結果會直接返回。
Java finally語句到底是在return之前還是之後執行