Java异常处理中同时有finally和return语句的执行问题
作者:My Technology Home 发布时间:2022-08-14 15:28:30
在Java中当try、finally语句中包含return语句时,执行情况到底是怎样的,finally中的代码是否执行,大家众说纷纭,有的说会执行,有的说不会执行,到底哪种说法正确,现在通过下面的例子加以说明:
第一种情况:try中包含return语句,finally中不包含
public class TestTry {
static String s="";
public static void main(String args[]){
s = test1();
System.out.println("8 "+s);
}
public static String test1(){
try{
System.out.println("try.....");
return s = "a";
}
finally{
s="b";
System.out.println("17 "+s);
}
}
}
这里我们定义了一个字符串 s,在try里面将"a"赋值给s,并直接返回,在finally里面把"b"赋值给s,最终s的值是a还是b呢?下面是执行的结果
try.....
17 b
8 a
我们发现最后的结果是a,但是b优先于a打印出来了,这是为什么呢?通过debug单步调试我们发现,在执行try中的return之前会先执行finally中的代码,之后再执行return语句。如果finally中也包含return语句,会出现什么情况呢,我们看第二种情况。
第二种情况:try,finally中都包含return语句
我们将上面的代码稍作改动
public class TestTry {
static String s="";
public static void main(String args[]){
s = test1();
System.out.println("8 "+s);
}
public static String test1(){
try{
System.out.println("try.....");
return s = "a";
}
finally{
return s="b";
}
}
}
将finally中的s="b";直接改成return s="b";,会出现什么样的结果呢?字符串s是a还是b呢?
try.....
8 b
我们发现最后的打印结果是b。
我们知道return语句用在某一个方法中,一是用于返回函数的执行结果,二是用于返回值为void类型的函数中,仅仅是一个return语句(return ;),此时用于结束方法的执行,也即此return后的语句将不会被执行,当然,这种情况下return语句后不能再有其它的语句了。
public static int print() {
int c = 1;
try {
c++;
System.out.println("try执行中...");
return c+100; //--------1
} catch (Exception e) {
e.printStackTrace();
//return c; //--------4
} finally {
c++;
System.out.println("finally执行中...");
return c; //--------2
}
//return c; //---------3
}
程序执行的结果为:
run:
try执行中...
finally执行中...
3
成功构建 (总时间: 0 秒)
注意,2与3位置处的return语句只能有一个,并且2、3、4中必须有一个return语句,如果2出执行后方法就结束了,3处的语句得不到执行。
try语句块执行到1处时,会将会将函数的返回值存放到另外一个临时变量(不同与c的变量,它的值为102)中,由于未发生异常,紧接着将会执行finally语句块,2处又遇到一个语句块,并将返回值存放到临时变量(值为3)中,最终返回的是此处的临时变量的值,此处return执行完成后,该方法结束。
public static int print() {
int c = 1;
try {
c++;
System.out.println(c);
System.out.println("try");
return c+100; //--------1
}finally {
c++;
System.out.println(c);
System.out.println("finally");
}
}
上述代码中finally语句块中没有return语句,函数最终返回的是第一个临时变量的值,也即102,执行结果如下:
run:
try
finally
102
成功构建 (总时间: 0 秒)
结论:1.无论try里面有没有return语句,finally语句一定都会执行(不愧是finally,名字起的好)。
2.如果finally中没有return语句,try里面有return,那么在执行try中的return语句之前会先去执行finally中的代码,再去执行try中的return语句;如果在finally中也包含return语句,将会直接返回,不再去执行try中的return语句。


猜你喜欢
- 本项目为大家分享了Java实现简单计算器功能的具体代码,供大家参考,具体内容如下一 项目说明实训目的:掌握 Java GUI 开发中的布局管
- 开始学习WebSocket,准备用它来实现一个在页面实时输出log4j的日志以及控制台的日志。首先知道一些基础信息:1.java7 开始支持
- 封装(Encapsulation)是面向对象编程的一个核心概念,它意味着将数据(属性)和方法(操作数据的函数)捆绑在一起,形成一个类(Cla
- 在开始之前,我先卖个关子提一个问题:假设我们有一个Movie类,这个类有三个成员变量分别是starred(是否收藏), title(电影名称
- 最初,XML 语言仅仅是意图用来作为 HTML 语言的替代品而出现的,但是随着该语言的不断发展和完善,人们越来越发现它所具有的优点:例如标记
- 目录什么是抽象类和接口? 区别在哪里?抽象类接口抽象类和接口解决了什么问题?如何模拟抽象类和接口如何决定该用抽象还是接口?什么是抽象类和接口
- CompletableFuture 介绍CompletableFuture是1.8引入的新特性,一些比较复杂的异步计算场景,尤其是需要串联多
- import java.io.File;import java.util.ArrayList;public class FileTest {
- 1. 生命周期感知1.1 生命周期感知组件我们知道,Controller(Activity or Fragment) 都是有生命周期的,但是
- 作者:冰封一夏出处:http://www.cnblogs.com/bfyx/HZHControls官网:http://www.hzhcont
- 本文将基于Spring Boot介绍两种生成二维码的实现方式,一种是基于Google开发工具包,另一种是基于Hutool来实现;
- 在android中的webview中,可以对文本内容进行对齐,具体方法如下 public class MainActivity
- 字符流是针对字符数据的特点进行过优化的,因而提供一些面向字符的有用特性,字符流的源或目标通常是文本文件。 Reader和Writer是jav
- 本文使用的Unicode+DLL+Debug的方式,因为不想最后生成的exe文件太大。环境搭建步骤如下:1、下载wxWidgets包:登录w
- 单例模式动机有时候只有一个类的实例是很重要的。比如,一个系统应该只有一个窗口管理实例。单例模式是最简单设计模式:类负责实例化自己,确保只有一
- Jmeter是纯Java开发的, 能够运行Java程序的系统一般都可以运行Jmeter, 如:Windows、 Linux、 mac等。由于
- 创建一个用户类类型的集合,手动输入用户库主要是判定输入的用户名和密码是否与库中的匹配做好区别是用户名输入错误还是密码输入错误的提示。定义用户
- 目录引言简单遍历筛选符合某属性条件的List集合获取某属性返回新的List集合获取以某属性为key,其他属性或者对应对象为value的Map
- 循环结构分两大类,一类是当型,一类是直到型。当型:当布尔值表达式条件为True时,反复执行某语句,当布尔表达式的值为False时才停止循环,
- 抛出问题:Long a = 4l;Long b = 4l;a == b //trueLong a = 128l;Long b = 128l;