Mysterious Bacteria (唯一分解++欧拉素数筛)
Dr. Mob has just discovered a Deathly Bacteria. He named it RC-01. RC-01 has a very strange reproduction system. RC-01 lives exactly x days. Now RC-01 produces exactly p new deadly Bacteria where x = bp (where b, p are integers). More generally, x is a perfect pth power. Given the lifetime x of a mother RC-01 you are to determine the maximum number of new RC-01 which can be produced by the mother RC-01.
Input
Input starts with an integer T (≤ 50), denoting the number of test cases.
Each case starts with a line containing an integer x. You can assume that x will have magnitude at least 2 and be within the range of a 32 bit signed integer.
Output
For each case, print the case number and the largest integer p such that x is a perfect pth power.
Sample Input
3
17
1073741824
25
Sample Output
Case 1: 1
Case 2: 30
Case 3: 2
题目大意:
给你一个数x = b^p,求p的最大值
x = p1^x1*p2^x2*p3^x3*...*ps^xs
开始我以为是找x1、x2、... 、xs中的最大值,后来发现想错了,x = b^p, x只有一个因子的p次幂构成
如果x = 12 = 2^2*3^1,要让x = b^p,及12应该是12 = 12^1
所以p = gcd(x1, x2, x3, ... , xs);
比如:24 = 2^3*3^1,p应该是gcd(3, 1) = 1,即24 = 24^1
324 = 3^4*2^2,p应该是gcd(4, 2) = 2,即324 = 18^2
本题有一个坑,就是x可能为负数,如果x为负数的话,x = b^q, q必须使奇数,所以将x转化为正数求得的解如果是偶数的话必须将其一直除2转化为奇数
#include<cmath>
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
typedef long long ll;
const int maxn = 1e6+5;
bool IsPrime[1000010];
int Prim[1000010],num = 0;
void init(){
int j;
for(int i = 2; i <= maxn; i ++){
if(!IsPrime[i])
Prim[num ++] = i;
for(j = 0; j < num; j ++){
if(i * Prim[j] > maxn)
break;
IsPrime[i * Prim[j]] = true;
if(i % Prim[j] == 0)
break;
}
}//printf("%d\n",num);
}
int gcd(int a,int b){
return !b?a:gcd(b,a%b);
}
int main()
{
init();
int t,ncase = 1;
scanf("%d",&t);
while(t--){
bool falg = false;
ll n;
scanf("%lld",&n);
if(n<0) {
falg = true;
n = -n;
}
int ans = 0;
for(int i = 0;i<num && Prim[i]<=n ; i++){
//if(n == 1) break;
int s = 0;
if(n%Prim[i] == 0){
while(!(n%Prim[i])){
s++; n /= Prim[i];
}
if(!ans) ans = s;
else ans = gcd(ans,s);
}
}
if(n!=1) ans = 1;
if(falg){
while(!(ans&1)){
ans >>= 1;
}
}
printf("Case %d: %d\n",ncase++,ans);
}
return 0;
}