c - 递归函数有一些限制吗?例如 : how many layers does the function require?

标签 c recursion stack-overflow collatz

制作了一个递归函数,它给出了给定起始编号的 collat​​z 序列中有多少项,例如代码 n=13:

int collatz(long n,long o)
{
    if (n!=1) {
        if(n%2==0)
            return collatz(n/2,o+1);
        else
            return collatz((n*3)+1,o+1);
    } else
        printf("%ld\t",o);
}
void main()
{
    collatz(13,0);
}

函数按预期运行;然而,对于一些整数,例如“n=113383”,有些东西会溢出(我猜)并返回:

Process returned -1073741571 (0xC00000FD)   execution time : 4.631 s
Press any key to continue.

请原谅我的非技术解释,非常感谢!

最佳答案

C 标准本身对递归深度没有限制。您可能会导致堆栈溢出,但堆栈大小在不同的环境中是不同的。我认为 Windows 有 1MB,Linux 有 8MB。它还取决于函数堆栈帧的大小,而这又取决于它有多少变量和哪种类型。

在您的例子中,您有两个 long 变量,每个变量可能是 8 个字节。您还有 5 个字节的字符串 "%ld\t",它可能最终出现在堆栈中,但我不确定。最重要的是,你有两个指向函数返回地址和前一个堆栈帧的指针的开销,它们在 64 位系统上各为 8 个字节。所以你的函数的堆栈帧大约是 32 个字节左右。也许多一点。所以在 Linux 系统上,我猜你的函数会在大约 200'000 的深度崩溃。

如果这是一个问题,请考虑将函数重写为非递归变体。查看 Blaze 答案,了解如何为您的案例完成此操作。正如 andreee 在下面评论的那样:

Additional note: You can increase the stack size under Linux with ulimit -s (also possible: ulimit -s unlimited) and in MSVC you can set the /F compilation flag to increase the stack size of your program. For MinGW, see this post.

关于c - 递归函数有一些限制吗?例如 : how many layers does the function require?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55969521/

相关文章:

c++ - 循环抛出 "parser stack overflow, program too complex"的编译时间

c - Vista 和 XP 的区别 [C]

javascript - 遍历树并获取每个对象的深度

c++ - 递归函数抛出非空函数结束警告

由于递归方法调用而导致Java堆栈溢出

c++ - 为什么没有发生堆栈溢出?

c++ - memcpy 将 float 转换为 int

c - 在多个线程中独立运行 Boehm GC

c - valgrind : Why is my tiny programming allocating so much space?

java - 二元递归搜索