hdu3826-Squarefree number-(欧拉筛+唯一分解定理)

Squarefree number

Time Limit: 10000/3000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 3691    Accepted Submission(s): 971

 

Problem Description
In mathematics, a squarefree number is one which is divisible by no perfect squares, except 1. For example, 10 is square-free but 18 is not, as it is divisible by 9 = 3^2. Now you need to determine whether an integer is squarefree or not.
 

Input

The first line contains an integer T indicating the number of test cases.
For each test case, there is a single line contains an integer N.

Technical Specification

1. 1 <= T <= 20
2. 2 <= N <= 10^18
 
Output
For each test case, output the case number first. Then output "Yes" if N is squarefree, "No" otherwise.
 
Sample Input
2 30 75
 
Sample Output
Case 1: Yes Case 2: No
 
翻译:输入一个n,如果可以被一个平方数整除,则不是平方自由数,输出no,否则输出yes
分析:显然要分解质因数,根据唯一分解定理分解。
n<=10^18,不能用暴力求到10^9的素数,欧拉筛一般只是找10^6内的素数。显然需要优化。
如果n>10^6,巨大,筛完了10^6内的质因子后,n还是大于10^6,则
1.如果n不是平方自由数,则因子中包含质因数的平方,则n=p*p,p是素数,p>10^6,除此之外没有别的大于10^6的因子了,否则n>10^18
2.如果n是平方自由数,则因子中不包含质因数的平方
(1)n是素数
(2)n不是素数,n=p1*p2,是两个大素数的乘积。p1,p2>10^6
 1 #include<stdio.h>
 2 #include<iostream>
 3 #include<algorithm>
 4 #include<cstring>
 5 #include<math.h>
 6 #include<string>
 7 #include<map>
 8 #define ll long long
 9 #define inf 0x3f3f3f3f
10 using namespace std;
11 
12 ll prime[1000086];
13 ll cnt,t,n;
14 int maxx=1e6+5;
15 bool vis[1000086];
16 
17 
18 void init()
19 {
20     memset(vis,true,sizeof(vis));
21     vis[0]=vis[1]=false;
22     cnt=0;
23     for(ll i=2;i<=maxx;i++)
24     {
25         if(vis[i])
26             prime[cnt++]=i;
27         for(ll j=0;j<cnt && i*prime[j]<=maxx;j++)
28         {
29             vis[ i*prime[j] ]=false;
30             if( i%prime[j]==0 ) break;
31         }
32     }
33 }
34 
35 int main()
36 {
37     init();
38     scanf("%lld",&t);
39     for(ll k=1;k<=t;k++)
40     {
41         bool flag=false;
42         scanf("%lld",&n);
43         for(ll i=0;i<cnt && !flag;i++)
44         {
45             int num=0;
46             while( n%prime[i]==0 )///分解质因子
47             {
48                 n=n/prime[i];
49                 num++;
50             }
51             if(num>=2)
52             {
53                 flag=true;
54                 break;
55             }
56         }
57         /*分解完所有小于10^6的质因子,出来后的这个n还大于1的有三种情况
58         第一种情况,是一个 大于10^6 的素数
59         第二种情况,是两个 大于10^6 的素数 的乘积,不可能还有第三个大于10^6的质因子
60         第三种情况,是一个 大于10^6 的素数 的平方,不可能还有第三个大于10^6的质因子
61         */
62         if(!flag && n>1)
63         {
64             ll temp=(ll)sqrt(n);
65             if(temp*temp==n)
66                 flag=true;
67         }
68         if(flag)
69             printf("Case %lld: No\n",k);
70         else
71             printf("Case %lld: Yes\n",k);
72     }
73     return 0;
74 }

 

posted @ 2019-02-09 14:10  守林鸟  阅读(587)  评论(0编辑  收藏  举报