我试图找出所有素数高达200万的总和。
所以我为它编写了以下代码:
#include <math.h>
#include <stdlib.h>
#define limit 2000000
int main(void)
{
unsigned int *sieve, i, j;
unsigned long long int sum = 0;
sieve = malloc(sizeof(int)*limit);
for(i=2;i<=limit;i++)
sieve[i] = 1;
for(i=2;i<=limit;i++)
{
if(sieve[i])
{
for(j=i;j*i<=limit;j++)
sieve[j*i] = 0;
}
}
for(i=2;i<=limit;i++)
{
if(sieve[i])
sum += i;
}
printf("The sum is %llu\n",sum);
return 0;
}
答案应该是142913828922
,但我得到142889228620
。
你能告诉我出了什么问题吗?我无法理解。
答案 0 :(得分:3)
unsigned int *sieve, i, j;
for(j=i;j*i<=limit;j++)
j*i
的计算i > 65535
溢出。在这种情况下,虚假地产生一些伪复合材料。
当i
达到极限的平方根时停止筛分。
答案 1 :(得分:3)
我认为,你错误的malloc记忆筛选。 尝试:
sieve = malloc(sizeof(int)*limit + 1);
答案 2 :(得分:2)
您可以在第一个循环中添加总和,并避免乘以可能溢出的i * j。 还为限制+ 1项分配空间。
for(i=2;i<=limit;i++)
{
if(sieve[i])
{
// Add to sum
sum += i;
// Zero all multiples of i, up to limit
for(j=i; j <= limit; j+=i)
sieve[j] = 0;
}
}
printf("The sum is %llu\n",sum);
上面的代码为我提供了你想要的结果。