hdu3892 Common Roots 最大取模公因式

来源:互联网 发布:淘宝上的拔步床能买吗 编辑:程序博客网 时间:2024/06/06 18:41

We have many polynomials modulo p (p is a prime number). An interesting issue would be to determine whether they have some roots in common. Notice roots we mention here are integers in modulo p system (0 <= root < p). Moreover, if the given polynomial is of order r, we will guarantee that it has r roots.
For example, we have
x^2 + 13x + 36 (mod 37)
x^3 + 14x^2 + 49x + 36 (mod 37)
If x = 33 or x = 28, both of them would give the value of 0. So 33 and 28 are the roots in common.
 

Input
There are many test cases (less than1000).
In each case, the integer in the first line is n (the number of polynomials in this case). Then n lines followed. Each of them starts with an integer r (order of polynomials, r <= 50), and r + 1 integers (a(r), a(r-1) ,..., a(0)), which means the polynomial goes like:
a(r) * x^r + a(r-1) * x^(r-1) + … +a(1) * x + a(0) (mod 999983).
To make it easier, p is set to be 999983, as you see.
 

Output
For each case, just output “YES” if they have common roots, otherwise “NO” in a single line.
 

Sample Input
22 1 13 363 1 14 49 36
 

Sample Output
YES

  是否存在解,满足每个式子取模后都为0。

  求出这些式子的公因式,如果最大系数大于0的话肯定有解。

#include<iostream>#include<queue>#include<cstring>#include<cstdio>#include<cmath>#include<set>#include<map>#include<vector>#include<stack>#include<algorithm>#define eps 1e-9#define MAXN 1010#define MAXM 110#define MOD 999983typedef long long LL;using namespace std;LL N,M;vector<LL> ans,g[MAXN];void gcd(LL a,LL b,LL& d,LL& x,LL& y){    if(!b){        d=a;        x=1;        y=0;    }    else{        gcd(b,a%b,d,y,x);        y-=x*(a/b);    }}LL inv(LL a,LL n){    LL d,x,y;    gcd(a,n,d,x,y);    return d==1?(x+n)%n:-1;}vector<LL> poly_gcd(vector<LL> a,vector<LL> b){    if(!b.size()) return a;    int L=a.size()-b.size()+1,bs=b.size(),as=a.size();    for(LL i=0;i<L;i++){        LL t=(a[i]*inv(b[0]%MOD,MOD))%MOD;        for(LL j=0;j<bs;j++) a[i+j]=(a[i+j]-b[j]*t%MOD+MOD)%MOD;    }    vector<LL> c;    LL flag=0;    for(LL i=0;i<as;i++){        if(a[i]){            flag=1;            for(LL j=i;j<as;j++) c.push_back(a[j]);        }        if(flag) break;    }    return poly_gcd(b,c);}int main(){    freopen("in.txt","r",stdin);    LL cas=0;    while(scanf("%I64d",&N)!=EOF){        for(LL i=0;i<N;i++) g[i].clear();        for(LL i=0;i<N;i++){            scanf("%I64d",&M);            LL t;            for(LL j=0;j<M+1;j++){                scanf("%I64d",&t);                g[i].push_back(t);            }        }        if(N==1) ans=g[0];        else{            ans=poly_gcd(g[0],g[1]);            for(LL i=2;i<N;i++) ans=poly_gcd(ans,g[i]);        }        if(ans.size()>1) puts("YES");        else puts("NO");    }    return 0;}



0 0