计算阶乘(n)%m的递归方法中的分段错误

时间:2014-09-05 22:17:31

标签: c recursion factorial

我正在尝试使用n! % m中的递归来计算C。这是我正在使用的code

#include<stdio.h>
#define m 1000000007

long long int fact(long long int n) {
    if(n == 1)
        return (1);
    long long int n2 = (long long int)(fact(n-1));
    long long int k = (n*n2)%m;
    return k;
}

int main() {
    printf("%lld",fact(1000000));
}

这个程序给出了SEGMENTATION FAULT,但是如果我用迭代方法替换fact函数,那么程序打印正确答案。迭代fact函数是

long long int fact(long long int n){
    long long int k =1;
    long long int i;
    for(i = n;i>1;i--)
        k = (k*i)%m;
    return k; 
}

那么为什么迭代方法有效但递归方法失败了?

2 个答案:

答案 0 :(得分:4)

尝试gdb,但可能是因为你达到了你的最大递归深度,换句话说就是字面上耗尽了“内存”或基于你操作系统的当前规则集。

答案 1 :(得分:2)

如果您的C编译器优化尾调用,您可以将递归函数重写为尾递归函数:

long long int fact_aux(long long int n, long long int acc) {
    if(n <= 1)
        return acc;
    return fact_aux(n-1, (n * acc)%m);
}

long long int fact(long long int n) {
     return fact_aux(n, 1);
}

请注意,C标准不要求TCO,因此您无法保证这将与循环一样有效。 GCC does it