C++中未返回值的递归函数为何返回固定值且赋值后变化?
无return的非void C++函数行为分析
核心前提
C++标准明确规定:非void类型的函数如果没有通过return语句返回值就结束执行,属于未定义行为。这种情况下,函数的返回值完全是随机的,取决于编译器实现、当前调用栈的残留数据、编译优化等级等因素,没有任何可预测性。
为什么函数能返回值?
你编写的get_largest_in_fibonacci是返回int类型的函数,但else分支仅递归调用了自身,没有添加return语句传递递归结果。当递归到current因32位整数溢出变为负数时,会执行return before将值返回给上一层递归,但上层递归并没有把这个值继续return出去,而是直接结束函数。此时函数退出时没有提供合法的返回值,编译器会从调用栈的某个位置(比如调用约定中用来存放返回值的寄存器、栈顶的残留数据)取一个值当作返回值——这就是你看到“函数能返回值”的原因,但这个值没有任何实际意义。
为什么两种调用方式返回值不同?
- 直接在
cout中调用函数:此时编译器的调用栈布局、寄存器使用状态刚好让某个位置残留了数值2,因此输出结果为2。哪怕修改初始参数,只要栈的残留值未变,结果就会保持2。 - 将返回值赋值给变量再输出:此时编译器对代码的处理逻辑发生了变化(比如优化策略调整、栈的分配位置不同),调用栈里的残留数值变成了0,因此输出结果为0。
这两种情况都是未定义行为的典型表现,换个编译器、调整编译优化等级(比如开启O2优化),结果可能变成其他随机数,甚至出现程序崩溃的情况。
内容的提问来源于stack exchange,提问作者codeDog
相关产品推荐
相关产品推荐

