codeforces 338D GCD Table

什么都不会只能学数论QAQ

英文原题不贴了

题意:

有一张N*M的表格,i行j列的元素是gcd(i,j)
读入一个长度为k,元素大小不超过10^12的序列a[1..k],问这个序列是否在表格的某一行中出现过

1<=N,M<=10^12
1<=k<=10^4

首先显然x=lcm(a[i])

然后(y+i-1)%a[i]==0

即y%[i]=1-n

然后就神奇地变成了中国剩余定理

求出x和y后判无解即可,情况比较多

首先如果x和y超过n,m的范围或<0显然不对

然后注意枚举i看gcd(x,y+i-1)是否等于a[i]

恩?好像也不多

注意因为这个表示直接定义好的并没有实质地给出来,所以n,m都可以把int爆了

所有的计算过程都需要longlong?

什么都不会只能学数论QAQ

代码:

 1 #include<iostream>
 2 #include<cstdio>
 3 #include<algorithm>
 4 #include<cstring>
 5 #include<cmath>
 6 using namespace std;
 7 #define ll long long
 8 ll rd(){ll z=0,mk=1;  char ch=getchar();
 9     while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)mk=-1;  ch=getchar();}
10     while(ch>=‘0‘&&ch<=‘9‘){z=(z<<3)+(z<<1)+ch-‘0‘;  ch=getchar();}
11     return z*mk;
12 }
13 ll n,m,o;  ll mo[11000],a[11000];
14 ll exgcd(ll a,ll b,ll &x,ll &y){
15     if(!b){  x=1,y=0;  return a;}
16     ll d=exgcd(b,a%b,x,y);
17     ll tmp=x;  x=y,y=tmp-a/b*y;
18     return d;
19 }
20 ll chn(){
21     ll M=mo[1],A=a[1],k,y;
22     for(int i=2;i<=o;++i){
23         ll tmp=a[i]-A,d=exgcd(M,mo[i],k,y);
24         if(tmp%d)  return -1;
25         ll tm=mo[i]/d;
26         k=(k*tmp/d%tm+tm)%tm,A+=k*M,M=M*mo[i]/d,A=(A+M)%M;
27     }
28     return A;
29 }
30 int main(){freopen("ddd.in","r",stdin);
31     cin>>n>>m>>o;
32     for(int i=1;i<=o;++i)  mo[i]=rd(),a[i]=1-i;
33     int y=chn();
34     ll x=1,d;
35     for(int i=1;i<=o;++i){
36         d=exgcd(x,mo[i],d,d);
37         x=x*mo[i]/d;
38     }
39     if(!y)  y=x;
40     if(y<0 || y+o-1>m || x>n){  cout<<"NO"<<endl;  return 0;}
41     for(int i=1;i<=o;++i)if(exgcd(x,y+i-1,d,d)!=mo[i]){  cout<<"NO"<<endl;  return 0;}
42     cout<<"YES"<<endl;
43     return 0;
44 }

时间: 2024-11-05 11:51:23

codeforces 338D GCD Table的相关文章

Codeforces 338D GCD Table 中国剩余定理

题目链接:点击打开链接 给定n*m的矩阵,[i,j]的点值为gcd(i,j) 给定一个k长的序列,问是否能匹配上 矩阵的某一行的连续k个元素 思路: 我们要求出一个解(i,j) 使得 i<=n && j<=m 此时输出 YES 对于j j % b[0] = 0 j+1 % b[1] = 0 ··· j+l % b[l] = 0 根据定理:若 a == b (mod n) => (a+c) == b+c (mod n) 所以将上式变换为 j % b[0] = 0 j % b

codeforces 582A. GCD Table 解题报告

题目链接:http://codeforces.com/problemset/problem/582/A 网上很多题解,就不说了,直接贴代码= = 官方题解: http://codeforces.com/blog/entry/20692 1 #include <iostream> 2 #include <cstdio> 3 #include <cstdlib> 4 #include <cstring> 5 #include <algorithm>

Codeforces Round #323 (Div. 2) C. GCD Table

C. GCD Table The GCD table G of size n × n for an array of positive integers a of length n is defined by formula Let us remind you that the greatest common divisor (GCD) of two positive integers x and y is the greatest integer that is divisor of both

SPOJ4491. Primes in GCD Table(gcd(a,b)=d素数,(1&amp;lt;=a&amp;lt;=n,1&amp;lt;=b&amp;lt;=m))加强版

SPOJ4491. Primes in GCD Table Problem code: PGCD Johnny has created a table which encodes the results of some operation -- a function of two arguments. But instead of a boring multiplication table of the sort you learn by heart at prep-school, he has

SPOJ PGCD - Primes in GCD Table (好题! 莫比乌斯反演+分块求和优化)

PGCD - Primes in GCD Table Johnny has created a table which encodes the results of some operation -- a function of two arguments. But instead of a boring multiplication table of the sort you learn by heart at prep-school, he has created a GCD (greate

Codeforces 338 D. GCD Table

http://codeforces.com/problemset/problem/338/D 题意: 有一张n*m的表格,其中第i行第j列的数为gcd(i,j) 给出k个数 问在这张表格中是否 有某一行中连续的某一部分 就是 这k个数 题意转化: 是否存在 一对i,j 满足gcd(i,j)=a1,gcd(i,j+1)=a2,…… gcd(i,j+k-1)=ak 直观上感觉: i要满足的必要条件是 i |  lcm(a1,a2……ak) j要满足的必要条件是 j= a1*k1,j+1=a2*k2…

CODEFORCES #523 C. GCD Table

题目描述: 有一个序列,给出该序列中的数两两的gcd,并打乱顺序,求原序列. 解题思路: 首先,原序列中的数一定会在新序列中出现,而且gcd(a, b) <= a, b.那么新序列中最大和次大的数一定是原序列中的数,那第三大是不是呢?显然要先去除已经确定的数的两两gcd,再找剩下的数最大数. 代码: 写完才发现写得有点蠢. 1 #include <cstdio> 2 #include <cstring> 3 #include <algorithm> 4 #incl

Codeforces #322 (Div. 2) C GCD Table

题意简述: 给定一个长度为$n$的序列 将这个序列里的数两两求$gcd$得到$n^2$个数 将这$n^2$个数打乱顺序给出 求原序列的一种可能的情况 ----------------------------------------------------------------------------------------------------------------------- 比赛时一直去想有什么特殊的性质(找规律) 比如这些数里为一个数的倍数的数一定是平方个 然而按照这样的思路去想又

【Codeforces 582A】GCD Table

[链接] 我是链接,点我呀:) [题意] 给你一个数组A[]经过a[i][j] = gcd(A[i],A[j])的规则生成的二维数组 让你求出原数组A [题解] 我们假设原数组是A 然后让A数组满足A[i]<Ai+1 然后我们要先想到一个不等式 a[i][j]=gcd(A[i],A[j])<=A[min(i,j)] 而miin(i,j)<=n 则a[i][j]<=A[n] 所以a[i][j]里面的最大值就是A[n] 之后,我们把gcd(A[n],A[n])删掉 这样剩余的n*n-1