一、finally的执行顺序
先来看一段代码
import java.util.*;
public class Main {public static void main(String[] args) {System.out.print(fun1());}public static String fun1() {try {System.out.print("A");return fun2();} finally {System.out.print("B");}}public static String fun2() {System.out.print("C");return "D";}
}
通过debug代码跟踪,执行顺序是 fun1()的try -> fun1()的return表达式 ->fun2() -> fun1()的finally -> fun1()进行返回表达式的值 ->回到main函数。 因此代码输出是:ACBD
总结执行过程就是:try中的return计算表达式后,等待finally执行完再返回表达式,具体的步骤就不多说了,可以参考这里https://blog.csdn.net/stduent_/article/details/60955365
这么做的好处是什么呢? 它保证了finally里的代码都会被执行到,无论try里调用了return,break,continue。 那么finally就非常适合用于释放。 此外,如果finally里有return,那么try里的return就不会执行,而是执行finally的return
二、try的值用局部变量保存
再看一段代码
import java.util.*;
public class Main {public int aaa() {int x = 1;try {return ++x;} catch (Exception e) {} finally {++x;}return x;}public static void main(String[] args) {Main t = new Main();int y = t.aaa();System.out.println(y);}
}
执行结果是2。
按照刚才的分析,try里面进行++x, finally进行++x, 最后try中的return执行返回, 这样x不是应该变成3吗?? 实际上JVM在try的return中,通过局部变量进行保存,最后返回的是局部变量。效果就是finally操作的数都不会再影响返回值
If the try clause executes a return, the compiled code does the following:
1.Saves the return value (if any) in a local variable.
2.Executes a jsr to the code for the finally clause.
3.Upon return from the finally clause, returns the value saved in the local variable.翻译如下:
如果try语句里有return,那么代码的行为如下:
1.如果有返回值,就把返回值保存到局部变量中
2.执行jsr指令跳到finally语句里执行
3.执行完finally语句后,返回之前保存在局部变量表里的值
总结
本篇讲了
1、finally语句的执行顺序
2、finally代码块读写数据不会返回,是利用了局部变量 ; 补充:但是如果修改静态变量,操作是有效的。