思路:
x里如果只有一个d,x只能被表示为d*a(d*a是一个漂亮数),找不到第二种符合条件的形式了。
x里如果有2个d,尝试把x表示成 d(一个漂亮数)* d*a(另一个漂亮数),是否还有第二种取决于a是合数还是质数,如果a是质数就没有了。若是合数肯定有,因为你可以把a分成两个数b,c ,然后把x表示为d*b(一个漂亮数) * d*c (另一个漂亮数)
x里如果有3个d,尝试把x表示成 d * d * (d*a) 同上面的情况,a如果是合数则肯定有。不同于上面的是,a如果是质数是有可能有另一种形式的,我们可以尝试把(d*a)分成两个b,c然后把x表示为d*b(一个漂亮数) * d*c (另一个漂亮数)
如果d也是质数,很显然是分不出来能使得d*b 是一个漂亮数 d*c 是另一个漂亮数的b,c
现在的问题是,如果d是合数,能不能分出符合条件的两个b,c,通过 128 4 这个样例 我们可以察觉到好像当d==a*a的时候是不能分出来的,现在就缺严谨的证明了
当d==a*a,d*a也就是 a^3,要分成两个都拿不出 a^2 的数是不可能的,
一共两种分法 a a^2,1 a^3 这两种分法都至少有一个数拿得出a^2 .
已经证明了d==a*a是不行的,那剩下的情况是不是一定可以呢?
如果d只有a这一个质因子,d==a^n(n>=3)d*a就可以分成 a^2 和 a^(n-1) 这两个数都拿不出d
现在看d存在非a的质因子的情况,为了叙述的方便,我们把d中非a的质因子记为e
d*a就可以分解成 e 和 d*a/e
e肯定拿不出d咯,d*a/e 要想拿出来d,只能让a==e了,这与我们的前提条件:e是d中非a的质因子矛盾,所以是拿不出d的
至此,我们严谨的证明出了:当a是质数,d是合数,只有在d==a*a时,不能把d*a分成两个我们想要的b,c.
再看看当x里有4个d,同样的,如果a,d都是质数肯定不行。a是合数肯定行,那a是质数,d是合数的情况呢?
上面已经证明过了:当a是质数,d是合数,只有在d==a*a时,不能把d*a分成两个我们想要的b,c. 所以只要d!=a*a,我们就可以找到第二种形式
但你要知道,这里有4个d了,这就意味着我们可以把d*a分成三个拿不出d的数
再来看看d==a*a,d*a就是a^3 我们可以把它分成3个a 就可以把 x表示为 d*a * d*a * d*a 这3个漂亮数相乘
所以,在x里有4个d时,a是质数,d是合数的情况下一定可以找到第二种形式
虽然我写的十分冗长,但还是很严谨的,重要的还是自己思考
AC代码
#include<iostream>
#include<string>
#include<queue>
#include<algorithm>
#include<set>
#include<cmath>
#include<cstring>
using namespace std;
typedef unsigned long long ll;
const int mod=12345;
const int maxn=1e6+10;
bool is_prime(int x)
{for(int i=2;i<=x/i;i++){if(x%i==0) return false;}return true;
}
int main()
{int t;cin>>t;while(t--){int x,d;cin>>x>>d;int cnt=0;while(x%d==0){cnt++;x/=d;}if(cnt==1) cout<<"NO"<<endl;else if(cnt==2){if(!is_prime(x)) cout<<"YES"<<endl;else cout<<"NO"<<endl;}else{if(is_prime(x)&&(is_prime(d)||(cnt==3&&d==x*x))) cout<<"NO"<<endl;else {cout<<"YES"<<endl;}}}
}