首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >有人能解释为什么这个递归函数崩溃吗?

有人能解释为什么这个递归函数崩溃吗?
EN

Stack Overflow用户
提问于 2022-04-01 21:19:57
回答 2查看 82关注 0票数 0

为什么这个递归(我不确定,我发现这段代码说它是“递归”的)代码崩溃(我在互联网上发现了这种奇怪的方法,但我真的不知道它是如何工作的)输入值>4000 (有时>4023,有时>4015,我真的不明白.)

代码语言:javascript
运行
复制
#include <iostream>
unsigned long long int sum(unsigned long long int k)
{
    if (k > 0) {
        return k + sum(k - 1);
    }
    else {
        return 0;
    }
}
int main()
{
    unsigned long long int n;
    std::cout << "This program prints the sum of the first N natural numbers.\n\
Enter N: _";
    std::cin >> n;
    std::cout << "The sum is: " << sum(n) << ".\n\
Press any key to exit...";
    system("pause>nul");
    return 0;
}

相反,这不是吗?

代码语言:javascript
运行
复制
#include <iostream>
int main()
{
    unsigned int n;
    std::cout << "Questo programma stampa la somma dei primi N numeri naturali.\n\
Prego inserire N: _";
    std::cin >> n;
    unsigned long long int tmp = 0;
    for (n; n != 0; --n) {
        tmp += n;
        //std::cout << tmp << ' ';
    }
    std::cout << "La somma \212: " << tmp << ".\n\
Premere un tasto per uscire...";
    system("pause>nul");
    return 0;
}
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2022-04-01 21:24:01

递归版本每次调用自己时都会使用少量的堆栈空间,因此它受到堆栈大小的限制,如果它多次调用自己,则会崩溃。这是一个典型的堆栈溢出错误。

迭代的第二个版本没有这个问题。

票数 2
EN

Stack Overflow用户

发布于 2022-04-01 21:51:18

你的第一种方法

第一种方法是递归的。这意味着它对每一个k调用一次函数sum(),假设k是2,而sum()被调用两次,以此类推。

每个函数调用都需要在堆栈上为其参数、局部变量和一些管理数据(如堆栈指针)、程序在函数返回时跳到的返回地址以及其他一些内容占用空间。当您经常调用sum()时,让我们说大约4000次,堆栈上没有足够的空间供下一次调用sum()时使用。结果导致堆栈溢出,应用程序崩溃。

在应用程序崩溃之前,您可以提供的最大k值取决于您的系统。这意味着,在具有“大”堆栈的Windows、Linux或MacOS桌面上,您可以使用k=大约4000次调用函数,而在嵌入式系统中,每个线程的堆栈可能更低,应用程序也会更早崩溃。

你的第二种方法

第二种方法不是递归的,因此对其他函数的调用不需要堆栈上的任何额外空间。因此,您的应用程序不会崩溃,因为您没有从第一种方法获得堆栈溢出。

此外,您的第二种方法应该运行得更快,因为您不需要花时间进行许多函数调用。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/71712855

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档