【发布时间】:2020-04-20 07:04:02
【问题描述】:
我写了一个非常简单的程序来计算一个数的阶乘,问题是从大约 30 到 60,它返回一个负数,从 70 它返回 0。 我不知道我做错了什么。这个问题可能取决于我电脑的计算能力吗? 代码如下:
#include <stdio.h>
int main(){
int x, i;
long long int f = 1;
printf("Insert a number:");
scanf("%d", &x);
if (x == 0){
printf("0! = 1");
}
else {
for (i = 1; i <= x; i++){
f *= i;
}
printf("%d! è = %lli", x, f);
}
return 0;
}
【问题讨论】:
-
将 f 更改为 long long unsigned int,大量的 msb 为 1,表示负数
-
这不是你计算机的计算能力,而是一个 long long int 的范围,它甚至不足以表示任何接近 70 的东西!。 long long int 通常是 64Bit,这意味着可表示的最大数将是 2^63
-
@sergeyrar 这“修复”了负数,但结果仍然不正确(只是不太明显)。 64Bit 仍可表示的最高阶乘是 20!顺便说一句,任何比这更高的东西和常规整数类型都不会再削减它了
-
@Schiele 有,但是你不能再使用普通的整数类型和运算符了。本质上,您必须像在纸上那样进行乘法运算,并将数字存储为整数数组。然而,已经有许多库可以做到这一点,只需谷歌“bignum”或“bigint”
-
@Schiele 不,这些库(例如 gmp)提供了一组您必须使用的函数和数据类型。因此,您不必使用
f *= i,而是必须使用库提供的某种乘法函数。话虽如此,自己实现一个基本的 bigint 函数(如加法或乘法)并不是那么难,并且您可以在此过程中学到很多东西。您必须问自己是否只想尽快找到解决方案,或者借此机会了解有关 bigints 的更多信息。