【问题标题】:How recursion return the value? [duplicate]递归如何返回值? [复制]
【发布时间】:2020-08-13 16:53:07
【问题描述】:
1. #include<stdio.h> 

    int recursion_check(int i);

 
    main(){

         printf("%d",recursion_check(6));
    }
    
    int recursion_check(int i){
    
    if(i==0)
    return 5;
    
    else{
        recursion_check(i-1);
        }
        
    }

我正在从主函数调用一个函数(递归检查)并获取返回值,但在其他情况下没有返回,我如何获取返回值?

【问题讨论】:

  • 这只是侥幸。打开更多编译器警告,例如 -Wall 或等效警告,以了解潜在问题。
  • @Carcigenicate 作为记录,C 根本不需要。您可以定义一个具有int 类型但没有return 的函数,它将是一个有效的C 程序。另一方面,C++ 要求函数内的所有代码路径都有效返回(main 除外,为了与 C 兼容)。
  • @Blindy 它可能是一个有效的 C 程序,但函数的结果将是不确定的,对吧?通过“必须*”,我的意思是保证预期的行为。
  • 也许,也许不是。我的意思是看OP中的代码。只要您在常规平台(x86、x86_64)上使用“普通”编译器(gcc、msvc、icc)编译它,它总是会返回预期值,并且不会写入 rax 相同的值每次通话。它应该生成正确的代码,实际优化编译器将为更便携的代码输出,而不需要优化编译器。
  • (当然忽略尾递归优化或死代码消除,完全优化的编译器应该用负载5 指令替换整个调用)

标签: c function recursion return


【解决方案1】:

欢迎使用未定义的行为。

它在您的(假定的)普通计算机上工作的原因是因为在英特尔平台上,寄存器大小或更小的整数返回是通过写入RAX/EAX/AX 寄存器来完成的,因此这些平台上的大多数编译器将避免使用该寄存器如果他们可以避免,请进行计算。

因此,当您的函数最终到达有效的return 并写入RAX 寄存器,然后从整个调用链中返回时,最初调用您的递归函数的函数将读取RAX 并且它'会得到写过一次的5

当然,没有什么能阻止编译器不这样做。它不必使用RAX,也不必避免将其用于其他计算。因此,未定义的行为。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2018-04-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-03-14
    • 2019-09-16
    • 2015-12-16
    • 2015-06-30
    相关资源
    最近更新 更多