其实return和finally的执行顺序问题非常简单,你只有看看代码的指令就清楚咯

简介: 看看代码的指令就清楚咯


image.png

  最近在整理Java常见的面试题,刚好整理到return和finally的执行顺序问题,这个很多小伙伴比较困惑,所以波波老师就通过指令带大家彻底弄清楚下

return和finally的顺序问题

  分析如下的代码程序,给出输出结果,并给出原因

public class Demo02 {
    public static void main(String[] args) {
        Demo02 demo02 = new Demo02();
        System.out.println(demo02.getName("bobo"));
    }
    public String getName(String name){
        String res = "";
        try {
            res = name;
            return  res;
        }finally {
            res = "波波烤鸭";
        }
    }
}

  输出的结果是:bobo

  原因:通过指令分析我们可以发现在 return 代码执行的时候会将局部变量保存在  栈帧的顶部,然后在finally中修改的还是原来的栈帧位置的局部变量,最终返回的信息还是栈帧顶部的变量,所以finally代码块在return关键字之后会执行,但是不会改变栈帧顶部的信息。

指令分析

  首先我们要清楚在jvm中,每个线程都具有自己的虚拟机栈。当执行方法时,如上面的getName,就会创建一个栈帧(存储局部变量表,操作数栈等信息)进入虚拟机栈。每一个方法从调用到执行完毕,就是一个栈帧从虚拟机栈中入栈到出栈的过程。对应的栈帧情况为

image.png

ldc:将int,float或者String类型常量从常量池推送至栈顶。

astore:将栈顶引用型类型数据存入指定本地变量。

aload:将制定的引用类型变量推送至栈顶

查看关键的指令为:

image.png

还有一种情况需要注意,如果finally和try块中都有return关键字会怎么样呢?

public class Demo02 {
    public static void main(String[] args) {
        Demo02 demo02 = new Demo02();
        System.out.println(demo02.getName("bobo"));
    }
    public String getName(String name){
        String res = "";
        try {
            res = name;
            return  res;
        }finally {
            res = "波波烤鸭";
            return res; // 指令中返回的就不是栈帧顶部的数据了 而是 res 对应的栈帧位置
        }
    }
}

image.png

  通过指令我们可以看到在finally中的return关键字的指令返回的就是finally中的局部变量的信息,可以理解为finally中的return会覆盖掉try块中的return逻辑。




相关文章
|
11月前
|
安全 网络架构
如何理解子网掩码:概念、功能与应用
如何理解子网掩码:概念、功能与应用
1881 2
|
8月前
|
Ubuntu 机器人 开发工具
具身智能干货|ROS2理论与实践系列(一):ROS2概述与环境搭建
《ROS2理论与实践》系列课程主要由基础篇、核心篇、应用篇、进阶篇以及项目库五部分组成。本阶段为《ROS2理论与实践——核心篇》课程,核心篇课程设计以官方内容为标准,主要介绍ROS2中的通信机制与开发者工具,其中前者是整个ROS2框架中的核心构成,而后者则为开发者能够高效的构建应用程序提供有力支持。本阶段课程目的是帮助大家快速上手ROS2,为后续进阶奠定基础。
686 12
具身智能干货|ROS2理论与实践系列(一):ROS2概述与环境搭建
|
12月前
|
小程序 UED
axure rp原型设计基础
Axure RP原型设计基础‌
267 4
|
存储 安全 API
Windows Server 2022 21H2 本地域权限提升漏洞(PetitPotam)
Windows Server 2022 Standard/Datacenter 存在本地域权限提升漏洞,攻击者可通过使用PetitPotam工具进行获取服务器SYSTEM权限。
821 1
|
存储 分布式计算 资源调度
Hadoop生态系统集成问题
【5月更文挑战第6天】
152 1
|
设计模式 算法 JavaScript
编码之舞:探索编程语言的艺术
在数字世界的舞台上,编程语言是舞者的双脚,是艺术家的画笔,它们编织着虚拟与现实的交响曲。本文将带领读者穿梭于代码的海洋,探索编程语言背后蕴含的艺术性和创造力,以及如何通过技术感悟提升编程的境界。
上标下标汇总
上标下标汇总
2549 0
|
小程序 前端开发
uniapp 微信小程序v-show 不显示
uniapp 微信小程序v-show 不显示
547 0
|
Linux 虚拟化 Docker
如何查看Linux服务器架构是否可以运行docker?底层原理是什么?
如何查看Linux服务器架构是否可以运行docker?底层原理是什么?
802 0
|
Java Maven Android开发
maven一波流(6)——解决烦人的maven工程编码和jdk版本自动切换问题
背景 有时候拿过别人的工程使用,update project之后发现编码不对,中文全部乱码,然后jdk也自动变成了1.5版本,项目报了一大堆错误。 这时候老手心里还是很淡定,右击项目,在属性里修改下编码,然后在build path里面改下jdk版本,搞定。 后来再update project编码和jdk又自动变回去了,于是乎大怒,无奈又重新操作一遍。
474 0
maven一波流(6)——解决烦人的maven工程编码和jdk版本自动切换问题