我们经常会使用try/catch/finally语句块。当然,return关键字使用也是很平常的事,但是不知道大家有没有注意个这样一个问题。当在try语句块里面使用return语句,在finally里面去修改return所要返回的内容会出现什么情况。首先,我们知道return是结束方法的标志,一旦方法执行到return语句就将返回不再往下执行。其次,我们也知道,finally里面的语句是无论方法怎样执行,最后都要执行finally里面的语句。那么究竟是先执行return还是finally呢?下面通过两个小实验来解决这个问题。

首先看第一个例子:

public class TestTryCatch {public static void main(String[] args){TestTryCatch test = new TestTryCatch();System.out.println(test.fun());}public int fun(){int i = 10;try{//doing somethingreturn i;}catch(Exception e){return i;}finally{i = 20;}}
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
输出结果:10
  • 1

Ok很简单的一个例子,创建了一个方法fun,在方法里使用try/catch语句,方法要求返回值类型为int型。在try里面放回i,这个时候是10,但是在finally里面将i值修改为20。我们看到结果是10,好像是return先执行。那么接下来再看另一个例子:

public class TestTryCatch {public static void main(String[] args){TestTryCatch test = new TestTryCatch();System.out.println(test.fun());}public StringBuilder fun(){StringBuilder s = new StringBuilder("Hello");try{//doing somethings.append("Word");return s;}catch(Exception e){return s;}finally{string.append("finally");}}
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
输出结果:HelloWordFinally
  • 1

看结果似乎有点出乎意料了,因为这次finally里面修改的内容生效了。看代码其实差别不大,只是把返回值类型修改为StringBuilder了。那么这是为什么呢?下面就为大家解释一下其中到底是怎么执行的。

首先,拿第一个例子来说,可以在main方法里实现这样一条语句:int result = test.fun();我们知道这样做是没有问题的,但是大家都知道“=”号赋值是常量赋值。但是,方法的存放地址和常量的存放地址是不一样的,方法的存放在代码区的。上面我们把一个方法赋值给一个int型也没有报错。那是因为在声明方法是我们声明了返回值类型。那么编译器就会在代码的最前端预留一段返回值类型的内存。执行return的时候,就会把返回的内容写入到这段内存中

这样,执行“=”号赋值的时候,就能在内存中匹配到相同的类型。赋值便能成功。

弄清楚上面的道理之后,再来解释最开始提出的问题就容易多了。在执行了return之后,返回的值已经被写入到那段内存中了,finally再修改i的值,只是修改了后面代码段的i值,对返回段内存没有影响。至于第二个例子,再看下面这张图你就会明白。

我们可以看到,当返回值不是基本数据类型的时候,其是指向一段内存的,return将返回段指向一段内存,但是代码段的s依然是指向的同一段内存地址,所以当s修改它指向内存中的值的时候,其实也就修改了返回段指向内存中的值,所以最终的值改变了。

到底返回值变不变可以简单的这么记忆:当finally调用的任何可变API,会修改返回值;当finally调用任何的不可变API,对返回值没有影响。

总结一下:其实return与finally并没有明显的谁强谁弱。在执行时,是return语句先把返回值写入但内存中,然后停下来等待finally语句块执行完,return再执行后面的一段。

文章转自:https://blog.csdn.net/zoujian1993/article/details/45362931


http://www.taodudu.cc/news/show-4647881.html

相关文章:

  • float,double,decimal的区别于误解
  • lua和python谁更适用于嵌入MMORPG?
  • 包子笔记 - 借贷投资就相当于赌博
  • 谁是中国首富?
  • A5000 VS 3090,谁更强?
  • 愿岁月静好,始于初见,止于终老
  • 内网网速取决于网络设备,而外网网速取决于带宽和用户多少
  • java中父类与子类有相同属性调谁?取决于左边
  • 云计算面临的安全威胁,主要来自于哪几个方面?
  • 数据库中的数据依赖
  • 关于对数的有趣问题:lnx趋近于负无穷的速率与lnx趋近于正无穷的速率一样吗?对数的平方趋近于无穷的速率相当于x的几次方?
  • 2020年编程语言趋势解读:编程世界之未来握于谁手?
  • 最新爆料 !公众号很有必要接入微社区吗?
  • 记录: 微信公众号部署之 单域名多公众号部署
  • 微信公众号如何运营才能吸引用户的关注?
  • 微信公众号菜单点击发送天气预报
  • 微信公众号接入AI聊天机器人
  • 公众号如何利用流量广告变现?
  • 公众号开通两周年了
  • 技术小白用python搭建微信公众号后台
  • php微信公众号无限制群发,微信公众号无限群发 - viki_php的个人空间 - OSCHINA - 中文开源技术交流社区...
  • 微信公众号消息回复
  • 微信新出“一键拒收”功能!公众号主怎么办?
  • php微信公众号支付vue,vue项目使用微信公众号支付总结及遇到的坑
  • 设计模式-流畅接口
  • 架构君公众号推荐 第一期
  • 接口思考小笔记
  • Python实现鸡兔同笼问题
  • 1007: 鸡兔同笼
  • Python 鸡兔同笼 编程题

return与finally到底谁先执行相关推荐

  1. java中return finally_Java中return和finally到底哪个先执行

    本章节我们从字节码的角度来探究下return和finally到底哪个先执行.下面先来看一段简单地源码:public class ReturnFinallyDemo { public static vo ...

  2. 各种有return的情况下try-catch-finally的执行顺序

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

  3. left join 一对多_MYSQL 连接查询算法:JOIN语句在 MYSQL 内部到底是怎么执行的

    前言 我们从一个问题引入今天的主题. 在日常业务开发中,我们可能经常听到 DBA 对我们说"不要"(注意:不是禁止)使用 join,那么为什么 DBA 对 join 这么抵触呢?是 ...

  4. try—catch—finally中,如果catch中return了,finally还会执行吗?

    1.如果catch中return了,finally还会执行吗 有异常 public class Test {public static void main(String[] args) {System ...

  5. Java如果在try里面执行return,那么还会不会执行finally?

    如果在try里面执行return,那么还会不会执行finally? 前言 我们都知道,finally在捕获异常的操作中,总是最后并且一定会执行的.那么,如果我在使用try finally的时候,如果t ...

  6. try-catch-finally 中,如果 catch 中 return 了,finally 还会执行吗

    finally 一定会执行 try-catch-finally中return的执行情况: 在try中没有异常的情况下try.catch.finally的执行顺序 try --- finally 如果t ...

  7. service中间调用dao层方法时,出现Mapper method ‘dao.xxx‘ has an unsupported return type错误,但是sql执行修改数据成功,并没有回滚

    原因:这个是因为dao层的sql执行成功后,返回的类型出现问题. 代码: service层:public Map<String, Object> updateActiveId(String ...

  8. java return在try中_在try的括号里面有return一个值,那在哪里执行fina

    除非在try块或者catch块中调用了退出虚拟机的方法(即System.exit(1);),否则不管在try块.catch块中执行怎样的代码,出现怎样的情况,异常处理的finally块总是会被执行的. ...

  9. try catch中 在catch语句中有 return其后面的代码是不执行的

    这只是一个笔记, 如题 public function tea(){try{10/0;}catch(\Exception $e){return 123;}$res = JWT::decode(&quo ...

最新文章

  1. java 彩票系统_JAVA版彩票随机生成系统
  2. 【FPGA】双端口RAM的设计(同步读写)
  3. 单例-重写new方法
  4. Document Builder: directly change element in Webdynpro ui
  5. 好用到哭!你需要立刻学会的20个Python代码段,你get到了吗?
  6. xgboost参数_具有贝叶斯优化的XGBoost和随机森林
  7. 华为数据库2019年度大盘点
  8. match_parent和fill_parent有什么区别?
  9. php页面打开响应时间
  10. android 时间差格式化,计算2天之间的时间差android
  11. django 学习个人总结 之many_to_one
  12. 备考OCJP认证知识点总结(一)
  13. 南邮80c51汇编语言编程实验,实验三 查表 多分支(80C51单片机汇编语言编程)
  14. var/let/const、块级作用域、TDZ、变量提升
  15. 尚硅谷李立超老师讲解web前端---笔记(持续更新)
  16. PTA 7-161 双曲余弦函数(*)
  17. Python爬取热门微博,并存储到MySQL中
  18. Python破解WIFI密码完整源代码,实测可成功破解
  19. 雷军:从金山“宰相”到小米“沙皇”
  20. 关于UIview UIlabel Unbutton 的一些常用的属性方法(用以优化界面)

热门文章

  1. C#中文和UNICODE编码转换【转】
  2. DevOps教程:DevOps 工具
  3. 好强型性格分析,如何改变好强型性格?
  4. 东风标致3008 1.6T 让人心动的价格诱惑
  5. 解决“error ‘else’ without a previous ‘if’”错误
  6. 观察者模式——应聘者和应聘公司的关系
  7. (MB) MRM域中的物理格式
  8. 路缘石成型机的安装使用和施工
  9. ReFi夏季升温:Uniswap v3和绿色资产池在Celo上启动
  10. 稻盛和夫修的是什么心?