C. Koxia and Number Theory
g c d ( a [ i ] + x , a [ j ] + x ) = = 1 gcd(a[i] + x, a[j] + x) = = 1 gcd(a[i]+x,a[j]+x)==1
辗转相减法
g c d ( a [ i ] + x , a [ j ] + x ) = g c d ( a b s ( a [ i ] − a [ j ] ) , a [ j ] + x ) gcd(a[i] + x, a[j] + x) = gcd(abs(a[i]-a[j]), a[j]+x) gcd(a[i]+x,a[j]+x)=gcd(abs(a[i]−a[j]),a[j]+x)
也就是说如果最大公约数不等于一,那么肯定是 a b s ( a [ i ] − a [ j ] ) 的因子 也就是说如果最大公约数不等于一,那么肯定是abs(a[i] - a[j])的因子 也就是说如果最大公约数不等于一,那么肯定是abs(a[i]−a[j])的因子
假设因子为p
( a [ j ] + x ) 的因子中不能有 p ,也就是 ( a [ j ] + x ) m o d p = = 0 (a[j] + x)的因子中不能有p,也就是(a[j] + x)modp == 0 (a[j]+x)的因子中不能有p,也就是(a[j]+x)modp==0
x ! = − a [ j ] m o d p 即 x ! = ( p − a [ j ] m o d p ) m o d p x != -a[j]modp 即 x!= (p -a[j]modp)modp x!=−a[j]modp即x!=(p−a[j]modp)modp
如果 x ! = 0 , 1 , 2 , 3 , . . . , p − 1 的话就说明无解,不存在 x 使 g c d = 1 如果x!= 0,1,2,3,...,p-1的话就说明无解,不存在x使gcd=1 如果x!=0,1,2,3,...,p−1的话就说明无解,不存在x使gcd=1
所以我们可以记录每个 p 上 x 不能等于数的个数,大于等于 p 就说明无解 所以我们可以记录每个p上x不能等于数的个数,大于等于p就说明无解 所以我们可以记录每个p上x不能等于数的个数,大于等于p就说明无解
只需要前一百的因子就够了
因为 n 小于 100 ,所以最多只会有 100 个不同的 a [ j ] 所以插入的数量也小于 100 ,所以只需要小于 100 的因子就够了,大于一百的也肯定不满足,因为数量不够 因为n小于100,所以最多只会有100个不同的a[j]所以插入的数量也小于100,所以只需要小于100的因子就够了,大于一百的也肯定不满足,因为数量不够 因为n小于100,所以最多只会有100个不同的a[j]所以插入的数量也小于100,所以只需要小于100的因子就够了,大于一百的也肯定不满足,因为数量不够
代码
#include<iostream>
#include<cstring>
#include<algorithm>
#include<set>
#include<unordered_map>
const int N = 1e5 + 10;
typedef long long ll;
using namespace std;
int pri[N];
bool vis[N];
ll arr[N];
int t, n;
int cnt;
void init_prime()
{
for(int i = 2; i < 110; i ++)
{
if(!vis[i])
{
pri[cnt++] = i;
}
for(int j = 0; j < cnt; j ++)
{
if(pri[j] * i > 110) break;
vis[pri[j]*i] = true;
if(i % pri[j] == 0) break;
}
}
}
int main()
{
unordered_map<int, set<int>> num;
unordered_map<ll,int> sam;
init_prime();
cin >> t;
while(t--)
{
bool f = 0;
num.clear();
sam.clear();
cin >> n;
for(int i = 0; i < n; i ++)
{
cin >> arr[i];
sam[arr[i]] ++;
if(sam[arr[i]] >= 2)
{
f = 1;
}
}
for(int i = 0; i < n; i ++)
{
for(int j = i+1; j < n; j ++)
{
ll t = abs(arr[i] - arr[j]);
for(int k = 0; k < cnt; k ++)
{
if(t % pri[k] == 0)
{
ll tem = pri[k];
num[tem].insert((tem - arr[j]%tem)%tem);
if(num[tem].size() == tem)
{
f = 1;
break;
}
}
}
}
}
if(f) puts("NO");
else puts("YES");
}
return 0;
}