【发布时间】:2014-09-14 04:53:18
【问题描述】:
代码输出满足条件的 (i,j) 对数
(2^j-1) % (2^i-1) == 0
在哪里
1<=i<j<=n
n 是用户输入的数字,在该数字下可以找到 (i,j) 对。 代码完美运行,但这段代码背后的逻辑是什么让人难以理解。
P.S: t 是一个变量,它允许用户一次输入多个数字。
#include<stdio.h>
#include<math.h>
int main()
{
int t;
long n,sum,ans;
scanf("%d",&t);
while(t--)
{
scanf("%ld",&n);
int nrt=(int)sqrt(n);
sum=0;
for(int i=1;i<=nrt;i++)
{
sum+=n/i;
}
ans=2*sum-nrt*nrt-n;
printf("%ld\n",ans);
}
return 0;
}
【问题讨论】:
-
有什么难的?
2^j是一个切换 2 位的 xor 操作; -1 从中减去一个。%运算符的 RHS 也有类似的操作。当 LHS 除以 RHS 时,%运算符给出余数。但是,看过代码后,我很困惑——关于(2^j-1) % (2^i-1) == 0的问题与显示的代码有什么关系?这是计算相同结果的另一种方法吗? -
@JonathanLeffler OP 几乎可以肯定在这种情况下(不是 C 代码)使用“^”来表示求幂。 “这是另一种计算相同结果的方法吗?” -- OP 说“代码输出满足条件的 (i,j) 对的数量......” -- 这是关系的明确陈述。
-
Prateek:最好问问写代码的人。他们可能会为您提供一篇数学文章,证明给定问题的这种解决方案。做出这样的证明可能并非易事。
-
“t 是一个变量,它允许用户一次输入多个数字”——只要
n的 scanf 成功,循环会好得多。 -
使用所有警告和调试信息 (
gcc -Wall -g) 编译您的程序。考虑scanf的返回值(它是成功扫描的项目数)。 使用调试器 (gdb)
标签: c algorithm math expression