不可摸数
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 10552 Accepted Submission(s): 2724
Problem Description
s(n)是正整数n的真因子之和,即小于n且整除n的因子和.例如s(12)=1+2+3+4+6=16.如果任何
数m,s(m)都不等于n,则称n为不可摸数.
数m,s(m)都不等于n,则称n为不可摸数.
Input
包含多组数据,首先输入T,表示有T组数据.每组数据1行给出n(2<=n<=1000)是整数。
Output
如果n是不可摸数,输出yes,否则输出no
Sample Input
3 2 5 8
Sample Output
yes yes no
一开始只想着找规律,WA两次后放弃了。直接暴力打表。。。
打到1000*1000就够用了。用筛选法求因子和。
AC代码:
#include <cstdio>
#include <cstring>
#include <cmath>
#include <cstdlib>
#include <algorithm>
#include <queue>
#include <stack>
#include <map>
#include <set>
#include <vector>
#define INF 0x3f3f3f
#define eps 1e-8
#define MAXN (1000000+1)
#define MAXM (100000)
#define Ri(a) scanf("%d", &a)
#define Rl(a) scanf("%lld", &a)
#define Rf(a) scanf("%lf", &a)
#define Rs(a) scanf("%s", a)
#define Pi(a) printf("%d\n", (a))
#define Pf(a) printf("%.2lf\n", (a))
#define Pl(a) printf("%lld\n", (a))
#define Ps(a) printf("%s\n", (a))
#define W(a) while(a--)
#define CLR(a, b) memset(a, (b), sizeof(a))
#define MOD 1000000007
#define LL long long
#define lson o<<1, l, mid
#define rson o<<1|1, mid+1, r
#define ll o<<1
#define rr o<<1|1
using namespace std;
map<int, int> fp;
int sum[MAXN];
void get()
{
for(int i = 1; i <= 1000000; i++)
{
if(i == 1)
sum[i] = 1;
else
sum[i] = i + 1;
}
for(int i = 2; i*i <= 1000000; i++)
{
for(int j = i; i*j <= 1000000; j++)
{
if(i == j)
sum[i*j] += i;
else
sum[i*j] += i + j;
}
}
for(int i = 2; i <= 1000000; i++)
fp[sum[i]-i] = 1;
}
int main()
{
get();
int t; Ri(t);
W(t)
{
int n; Ri(n);
//bool flag = (n==2||n==5);
printf(fp[n] ? "no\n" : "yes\n");
}
return 0;
}