Markdown版本笔记 我的GitHub首页 我的博客 我的微信 我的邮箱
MyAndroidBlogs baiqiantao baiqiantao bqt20094 baiqiantao@sina.com

异常 try catch finally return 执行关系 MD


目录

探讨finally语句的执行与return的关系

Java异常捕获机制try...catch...finally块中的finally语句是不是一定会被执行?不一定,至少有两种情况下finally语句是不会被执行的:

  • try语句没有被执行到,如在try语句之前就返回了,这样finally语句就不会执行,这也说明了finally语句被执行的必要而非充分条件是:相应的try语句一定被执行到。
  • 在try块中有System.exit(0)这样的语句,System.exit(0)是终止Java虚拟机JVM的,连JVM都停止了,所有都结束了,当然finally语句也不会被执行到。

1、finally语句是在try的return语句执行之后,return返回之前执行的

测试案例:

public class TestFinally {
public static void main(String[] args) {
System.out.println(test());
} public static String test() {
try {
System.out.println("try block");
if (new Random().nextBoolean()) {
return "直接返回";
} else {
return test2();
}
} finally {
System.out.println("finally block");
}
} public static String test2() {
System.out.println("return statement");
return "调用方法返回";
}
}

运行结果:

try block
finally block
直接返回

try block
return statement
finally block
调用方法返回

说明try中的return语句先执行了,但并没有立即返回,而是等到finally执行结束后再返回。

这里大家可能会想:如果finally里也有return语句,那么是不是就直接返回了,try中的return就不能返回了?看下面。

2、finally块中的return语句会覆盖try块中的return返回

public class TestFinally {
public static void main(String[] args) {
System.out.println(test());
} public static String test() {
try {
System.out.println("try block");
return "在try中返回";
} finally {
System.out.println("finally block");
return "在finally中返回";
}
// return "finally外面的return就变成不可到达语句,需要注释掉否则编译器报错";
}
}

运行结果:

try block
finally block
在finally中返回

这说明finally里的return直接返回了,就不管try中是否还有返回语句。

这里还有个小细节需要注意,finally里加上return过后,finally外面的return b就变成不可到达语句了,也就是永远不能被执行到,所以需要注释掉否则编译器报错。

3、如果finally语句中没有return语句覆盖返回值,那么原来的返回值可能因为finally里的修改而改变,也可能不变

测试用例:

public class TestFinally {
public static void main(String[] args) {
System.out.println(test());
} public static int test() {
int b = 20;
try {
System.out.println("try block");
return b += 80;
} finally {
b += 10;
System.out.println("finally block");
}
}
}

运行结果:

try block
finally block
100

测试用例2:

public class TestFinally {
public static void main(String[] args) {
System.out.println(test());
} public static List<Integer> test() {
List<Integer> list = new ArrayList<Integer>();
list.add(10086);
try {
System.out.println("try block");
return list;
} finally {
list.add(10088);
System.out.println("finally block");
}
}
}

运行结果:

try block
finally block
[10086, 10088]

这其实就是Java到底是传值还是传址的问题了,简单来说就是:Java中只有传值没有传址。

这里大家可能又要想:是不是每次返回的一定是try中的return语句呢?那么finally外的return不是一点作用没吗?请看下面

4、try块里的return语句在异常的情况下不会被执行,这样具体返回哪个看情况

public class TestFinally {
public static void main(String[] args) {
System.out.println(test());
} public static int test() {
int b = 0;
try {
System.out.println("try block");
b = b / 0;
return b += 1;
} catch (Exception e) {
b += 10;
System.out.println("catch block");
} finally {
b += 100;
System.out.println("finally block");
}
return b;
}
}

运行结果是:

try block
catch block
finally block
110

这里因 为在return之前发生了异常,所以try中的return不会被执行到,而是接着执行捕获异常的 catch 语句和最终的 finally 语句,此时两者对b的修改都影响了最终的返回值,这时最后的 return b 就起到作用了。

这里大家可能又有疑问:如果catch中有return语句呢?当然只有在异常的情况下才有可能会执行,那么是在 finally 之前就返回吗?看下面。

5、当发生异常后,catch中的return执行情况与未发生异常时try中return的执行情况完全一样

public class TestFinally {
public static void main(String[] args) {
System.out.println(test());
} public static int test() {
int b = 0;
try {
System.out.println("try block");
b = b / 0;
return b += 1;
} catch (Exception e) {
b += 10;
System.out.println("catch block");
return 10086;
} finally {
b += 100;
System.out.println("finally block");
}
//return b;
}
}

运行结果:

try block
catch block
finally block
10086

说明了发生异常后,catch中的return语句先执行,确定了返回值后再去执行finally块,执行完了catch再返回,也就是说情况与try中的return语句执行完全一样。

总结:

  • finally块的语句在try或catch中的return语句执行之后返回之前执行
  • 且finally里的修改语句可能影响也可能不影响try或catch中return已经确定的返回值
  • 若finally里也有return语句则覆盖try或catch中的return语句直接返回

2019-3-4

异常 try catch finally return 执行关系 MD的更多相关文章

  1. finally return 执行关系 异常处理 c#

    Return.finally执行关系简述 除了函数出现system.exit(0)终止虚拟机,finally中的代码一定执行,return语句会等待finally的执行:如果是值传递,finally中 ...

  2. java try catch finally return执行

    public static int testBasic(){ int i = 1; try{ i++; System.out.println("try block, i = "+i ...

  3. try catch finally return之间的关系

    一.try catch finally return之间的关系: 正在写dsoFramer的时候,同事突然说面试的时候问的一个问题,catch和return那个先执行,我瞬间迷茫了,然后整理了整理,稍 ...

  4. 有return的情况下try catch finally的执行顺序(转)

    结论:1.不管有木有出现异常,finally块中代码都会执行:2.当try和catch中有return时,finally仍然会执行:3.finally是在return后面的表达式运算后执行的(此时并没 ...

  5. try catch finally的执行顺序(有return的情况下)

    结论:1.不管有木有出现异常,finally块中代码都会执行:2.当try和catch中有return时,finally仍然会执行:3.finally是在return后面的表达式运算后执行的(此时并没 ...

  6. 有return的情况下try catch finally的执行顺序

    结论:1.不管有木有出现异常,finally块中代码都会执行:2.当try和catch中有return时,finally仍然会执行:3.finally是在return后面的表达式运算后执行的(此时并没 ...

  7. 有return的情况下try catch finally的执行顺序(最有说服力的总结)

    结论:1.不管有木有出现异常,finally块中代码都会执行:2.当try和catch中有return时,finally仍然会执行:3.finally是在return后面的表达式运算后执行的(此时并没 ...

  8. Java基础知识强化之IO流笔记06:有return的情况下try catch finally的执行顺序

    1. 给出结论: (1)不管有木有出现异常,finally块中代码都会执行:(2)当try和catch中有return时,finally仍然会执行:(3)finally是在return后面的表达式运算 ...

  9. 【Java疑难杂症】有return的情况下try catch finally的执行顺序

    有这样一个问题,异常处理大家应该都不陌生,类似如下代码: public class Test { public static void main(String[] args) { int d1 = 0 ...

随机推荐

  1. php和NodeJs共存的开发环境

    1 折腾 php nodejs 到一起 nodejs当然很火,就像着火了一样,但是必须承认要搭建一个前端的demo开发环境还是PHP靠谱, windows下可以非常的集成套件,比如http://www ...

  2. 格式化输出的方法:%、.format()、f

    a = '123'a1 = '456'a2 = '789' %占位符 text = "a=%s"%atext1 = "a=%s,a1=%s,a2=%s"%(a, ...

  3. 如何批量的在django中对url进行用户登陆限制

    参考URL: https://blog.csdn.net/hanshengzhao/article/details/79540306?utm_source=blogxgwz0 1,首先定义一个内部有装 ...

  4. [NOI2012]随机数生成器

    题解: 很显然是一道矩阵优化dp 然而表示我很智障地把式子一个个带入 然后就发现了为什么会有那些部分分(大概用扩欧是70吧) 注意用矩阵计算的时候要用快速乘(当然想写高精那也随便,时间无限宽裕) 代码 ...

  5. day9线程和进程

    进程:qq要以一个整体的形式暴露给操作系统管理,里面包含对各种资源的调用,内存的对各种资源管理的集合,就可称之为进程. 线程:是操作系统最小的调度单位,是一串指令的集合. 进程:要操作CPU,必须要先 ...

  6. 【spring基础】spring声明式事务详解

    一.spring声明式事务 1.1 spring的事务管理器 spring没有直接管理事务,而是将管理事务的责任委托给JTA或相应的持久性机制所提供的某个特定平台的事务实现.spring容器负责事物的 ...

  7. asp.net core2.0大白话带你入门

    本系列包括: 1.新建asp.net core项目2.web项目目录解读3.配置访问地址4.环境变量详解5.配置文件6.日志7.DI容器8.服务的生命周期9.session的使用10.cookie的使 ...

  8. Nordic Collegiate Programming Contest NCPC 2017-Problem D-Distinctive Character

    题目大意:给你n(n<=1e5)个二进制串 (每个串位数不超过20),定义两个串的相似度为对应 位置上相同的个数. 让你构造一个二进制串,使这个串与所给的这些串的相似度的最小值最大. 思路:刚开 ...

  9. P1865 A % B Problem 素数筛

    题目描述 区间质数个数 输入输出格式 输入格式: 一行两个整数 询问次数n,范围m 接下来n行,每行两个整数 l,r 表示区间 输出格式: 对于每次询问输出个数 t,如l或r∉[1,m]输出 Cros ...

  10. 【LeetCode】163. Missing Range

    Difficulty: Medium  More:[目录]LeetCode Java实现 Description Given a sorted integer array where the rang ...