我在c:
中这样做了#include<stdio.h>
int main (void)
{
int n,i;
scanf("%d", &n);
for(i=2;i<=n;i=i+2)
{
if((i*i)%2==0 && (i*i)<= n)
printf("%d \n",(i*i));
}
return 0;
}
解决这个问题的更好/更快的方法是什么?
答案 0 :(得分:6)
让我说明一个快速解决方案,以及如何推导它。从快速列出所有正方形并从那里开始工作(伪代码)开始:
max = n*n
i = 1
d = 3
while i < max:
print i
i += d
d += 2
所以,从4开始,只列出偶数方块:
max = n*n
i = 4
d = 5
while i < max:
print i
i += d
d += 2
i += d
d += 2
现在我们可以在while循环结束时缩短这个混乱:
max = n*n
i = 4
d = 5
while i < max:
print i
i += 2 + 2*d
d += 4
请注意,我们一直在使用2*d
,因此最好继续计算:
max = n*n
i = 4
d = 10
while i < max:
print i
i += 2 + d
d += 8
现在请注意,我们不断添加2 + d
,因此我们可以将其合并到d
中做得更好:
max = n*n
i = 4
d = 12
while i < max:
print i
i += d
d += 8
快速燃烧。计算每个方格只需要两次加法。
答案 1 :(得分:1)
我喜欢你的解决方案。我提出的唯一建议是:
(i*i)<=n
作为for循环的中间子句,然后先检查它,然后尽早退出循环。(i*i)%2==0
,因为'i'始终为正,而正平方始终为正。 答案 2 :(得分:0)
for (i = 2; i*i <= n; i+=2)
printf ("%d\t", i*i);
答案 3 :(得分:0)
循环中i
的最大值应该是n
的平方根的最低值。
原因是大于此值的任何i
(整数)的平方将大于n
。因此,如果您进行此更改,则无需检查i*i <= n
。
另外,正如其他人所指出的那样,检查i*i
甚至是没有意义的,因为所有偶数的平方都是偶数。
你正确地忽略奇数 i
,因为对于任何奇数i
,i*i
是奇数。
您的代码包含上述更改:
#include "stdio.h"
#include "math.h"
int main ()
{
int n,i;
scanf("%d", &n);
for( i = 2; i <= (int)floor(sqrt(n)); i = i+2 ) {
printf("%d \n",(i*i));
}
return 0;
}