使用最大有符号整数值时,project euler中的函数出错
我做euler问题是为了好玩,决定看看我的计算机能以多快的速度解决这个问题,最大的符号整数: 不幸的是,当我尝试使用最大的有符号int值2147483647时,我得到了一个负值(溢出?),如下图所示: 为什么我在使用使用最大有符号整数值时,project euler中的函数出错,c,integer-overflow,C,Integer Overflow,我做euler问题是为了好玩,决定看看我的计算机能以多快的速度解决这个问题,最大的符号整数: 不幸的是,当我尝试使用最大的有符号int值2147483647时,我得到了一个负值(溢出?),如下图所示: 为什么我在使用2147483647-1时得到了看似正确的答案,而在使用2147483647时得到了错误的值 这是我的密码 #include <stdio.h> int getsums(int v) { int sum, i; sum = i = 0; for(;i&l
2147483647-1
时得到了看似正确的答案,而在使用2147483647
时得到了错误的值
这是我的密码
#include <stdio.h>
int getsums(int v) {
int sum, i; sum = i = 0;
for(;i<v; i++){
if ( i%3 == 0 || i%5 == 0 ){
sum +=i;
}
}
return sum;
}
int main(void) {
int upperlimit = 0;
int sums = 0;
printf("Intervalo de 0 a (escreva um numero)\n");
printf(">>");
scanf("%d", &upperlimit);
sums = getsums(upperlimit);
printf("somas dos multiplos de 3 e 5 no intervalo [0;%d] e: %d\n", upperlimit, sums);
return 0;
}
#包括
int getsums(int v){
整数和,i;和=i=0;
对于(;i结果太大,无法放入int
类型,您应该使用无符号
类型,因为没有可能的负面结果,还可以将printf
的格式说明符更改为%u
:
unsigned int getsums(int v) {
unsigned int sum = 0;
int i = 0;
for(;i<v; i++){
if (i%3 == 0 || i%5 == 0 ){
sum +=i;
}
}
return sum;
}
int main(void) {
int upperlimit = 0;
unsigned int sums = 0;
printf("Intervalo de 0 a (escreva um numero)\n");
printf(">>");
scanf("%d", &upperlimit);
sums = getsums(upperlimit);
printf("somas dos multiplos de 3 e 5 no intervalo [0;%d] e: %u\n", upperlimit, sums);
return 0;
}
unsigned int getsums(int v){
无符号整数和=0;
int i=0;
对于(;i结果太大,无法放入int
类型,您应该使用无符号
类型,因为没有可能的负面结果,还可以将printf
的格式说明符更改为%u
:
unsigned int getsums(int v) {
unsigned int sum = 0;
int i = 0;
for(;i<v; i++){
if (i%3 == 0 || i%5 == 0 ){
sum +=i;
}
}
return sum;
}
int main(void) {
int upperlimit = 0;
unsigned int sums = 0;
printf("Intervalo de 0 a (escreva um numero)\n");
printf(">>");
scanf("%d", &upperlimit);
sums = getsums(upperlimit);
printf("somas dos multiplos de 3 e 5 no intervalo [0;%d] e: %u\n", upperlimit, sums);
return 0;
}
unsigned int getsums(int v){
无符号整数和=0;
int i=0;
对于((i)p>代码> int 和<代码>未签名< /代码>不足以存储该高输入的结果。您在另一种情况下得到的正数也不正确。要查看,请考虑<代码> INTHOMAX-3 <代码>(这或它上面的三个数字必须被<代码> 3 < /代码>整除)。。如果将前两个数字从INT\u MAX-3
添加到0
,则表示您肯定已经溢出INT\u MAX
,因为第二个数字肯定是>3
使用unsigned
在这里没有帮助,它只会帮助移动时间,直到溢出发生。UINT_MAX
大约是INT_MAX
的两倍,因此在添加前三个数字时,您将使其溢出,因为INT_MAX-3+INT_MAX-6
将达到大约UINT_MAX-9
。现在添加 INT_MAX-9
肯定会溢出UINT_MAX-9
,因为INT_MAX-9
肯定是>9
相反,使用uint64\u t
。将1
到2^31-1
的所有数字相加(即n*(n+1)/2
)不会超过<代码> 2 ^ 63 <代码>,所以您肯定会安全地使用<代码> 64 >代码>位。<> >代码> int 和<代码>未签名< /代码>不足以存储该高输入的结果。您在另一种情况下得到的正数也不正确。要看,请考虑<代码> INTXMAX -3 < /代码>。(这或上面的三个数字必须可以被3
)整除。如果将INT\u MAX-3
中的前两个数字加在0
上,则意味着您肯定已经溢出INT\u MAX
,因为第二个数字肯定是>3
使用unsigned
在这里没有帮助,它只会帮助移动时间,直到溢出发生。UINT_MAX
大约是INT_MAX
的两倍,因此在添加前三个数字时,您将使其溢出,因为INT_MAX-3+INT_MAX-6
将达到大约UINT_MAX-9
。现在添加 INT_MAX-9
肯定会溢出UINT_MAX-9
,因为INT_MAX-9
肯定是>9
相反,使用uint64\u t
。将1
到2^31-1
(即n*(n+1)/2
)之间的所有数字相加不会超过2^63
,因此使用64
位肯定是安全的。主要问题是int
不足以容纳总和
建议使用以下代码:
#include <stdio.h>
size_t getsums(size_t v)
{
size_t sum = 0;
for(size_t i=0; i<v; i++)
{
if ( i%3 == 0 || i%5 == 0 )
{
sum +=i;
}
}
return sum;
}
int main(void)
{
size_t upperlimit = 0;
size_t sums = 0;
printf("Intervalo de 0 a (escreva um numero)\n");
printf(">>");
scanf("%lu", &upperlimit);
sums = getsums(upperlimit);
printf("somas dos multiplos de 3 e 5 no intervalo [0;%lu] e: %lu\n", upperlimit, sums);
return 0;
}
以及以下各项:
Intervalo de 0 a (escreva um numero)
>>2147483646
somas dos multiplos de 3 e 5 no intervalo [0;2147483646] e: 1076060068317827348
主要问题是int
不够大,无法容纳和
建议使用以下代码:
#include <stdio.h>
size_t getsums(size_t v)
{
size_t sum = 0;
for(size_t i=0; i<v; i++)
{
if ( i%3 == 0 || i%5 == 0 )
{
sum +=i;
}
}
return sum;
}
int main(void)
{
size_t upperlimit = 0;
size_t sums = 0;
printf("Intervalo de 0 a (escreva um numero)\n");
printf(">>");
scanf("%lu", &upperlimit);
sums = getsums(upperlimit);
printf("somas dos multiplos de 3 e 5 no intervalo [0;%lu] e: %lu\n", upperlimit, sums);
return 0;
}
以及以下各项:
Intervalo de 0 a (escreva um numero)
>>2147483646
somas dos multiplos de 3 e 5 no intervalo [0;2147483646] e: 1076060068317827348
unsigned
是否足以保存总和?保存所有值的总和需要n*(n+1)/2
需要31位,大约是60
位。现在只取三分之一就需要超过56
位。所有这些都不可能包含在32
位中。我有什么地方弄错了吗?它将3或5的倍数相加。无符号
是否足以容纳总和?容纳所有值的总和取n*(n+1)/2
需要31位,大约是60位。现在每三分之一只需要超过56位。所有这些都不可能包含在32位中。我有什么地方弄错了吗?它把3或5的倍数相加。不要发布文本图像!当问运行时问题时,发布干净的代码y编译。发布的代码缺少#include
语句(我不想让您了解实际代码使用的头文件。为了便于我们人类阅读和理解:1)遵循公理:每行只有一条语句,并且(最多)每语句一个变量声明。2)变量名应指示内容
或用法
或更好。调用任何scanf()
函数族时,务必检查返回值(而不是参数值)为了确保操作成功。@user3629249我决定避免像这样一个简单问题的代码混乱,因为这是一个非常基本的euler项目练习。我认为很明显,我使用的是#包含编辑的问题。不要发布文本图像!当问运行时问题时,发布干净编译的代码。发布的代码缺少#include
语句(我不想让您了解实际代码使用的头文件。为了便于我们人类阅读和理解:1)遵循公理:只有一个