浅说Return
return是编程中常常涉及到的语句,其主要用途为被调用函数返回约定好的返回值,以便于调用函数接收。我们常常将该动作视作原子的,大多数情况下这个假设是正确的,但倘若不加以钻研,在某些场景下,其行为就会显得怪异而难以理解了。
汇编描述
对于return的行为,我们可以从C与汇编讲起。
这里给出了一个test函数,以及其汇编后的汇编码。
1 | int test(int a, int b){ |
可以看到,简单的一个return,被分为三个步骤:
- 准备返回值
- 调整栈帧
- 调整PC
又或者说分为两步,准备返回值与实际返回。
情景解析
在return的相关问题中,让人困惑的莫过于异常处理代码段中的return了。
1 | try{ |
我们知道,为了保证try、catch中打开的资源的关闭回收,finally语句必须执行,那么,假若我们在try、catch中进行了return,finally的执行能够得到保证吗?答案是——可以!其原理在于,在try、catch中执行return时,仅会执行return的第一部分——准备返回值,但是,并不实际进行返回,故得到实际流程如下:
graph LR; A(开始)-->B(try中语句)-->C(保存返回值)-->D(finally语句)-->E(实际返回);
当然,若是在finally中再次遇到return,就会将try/catch中的return准备的返回值覆盖咯。