HDU 3579 中国剩余定理 不互质的情况

#include <iostream>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <map>
#include <set>
#include <algorithm>
#include <ctime>
#include <vector>
#include <string>
#include <stack>
#include <queue>
using namespace std;
#define ll long long

ll ext_gcd(ll a,ll b,ll &x,ll &y)
{
    if(b==0)
    {
        x=1;y=0;
        return a;
    }
    ll x1,y1,d;
    d=ext_gcd(b,a%b,x1,y1);
    x=y1;
    y=x1-a/b*y1;
    return d;
}
ll gcd(ll a,ll b)
{
    if(b==0)
        return a;
    return gcd(b,a%b);
}
inline ll lcm(ll a,ll b)
{
    return a/gcd(a,b)*b;
}
ll linear_equation(ll a,ll b,ll n) // a=b(mod n)
{
    ll x,y,d;
    d=ext_gcd(a,n,x,y);
    if(b%d)
        return -1; // no solution
    ll e=x*b/d;
    return (e+n)%n;
}
ll merge_equation(ll a1,ll m1,ll a2,ll m2,ll &a,ll &m)
{
    ll d=gcd(m1,m2);
    if((a2-a1)%d)
        return -1; // no solution
    ll temp=linear_equation(m1/d,(a2-a1)/d,m2/d);
    m=m1/d*m2;
    a=(m1*temp+a1)%m;
    return 1;
}
ll a[100],m[100],vis[100];
int main ()
{
    int ncase,n,tt;
    ll M,ans,x,y,w;
    scanf("%d",&ncase);
    for(int kk=1;kk<=ncase;++kk)
    {
        bool flag=true;
        memset(vis,0,sizeof(vis));
        scanf("%d",&n);
        M=1;
        for(int i=1;i<=n;++i)
        {
            scanf("%I64d",&m[i]);
            M=lcm(M,m[i]);
        }
        for(int i=1;i<=n;++i)
            scanf("%I64d",&a[i]);
        for(int i=1;i<=n;++i)
        {
            for(int j=1;j<i;++j)
                if(!vis[j])
            {
                if(gcd(m[i],m[j])!=1)
                {
                    vis[j]=1;
                    tt=merge_equation(a[i],m[i],a[j],m[j],a[i],m[i]);
                    if(tt<0)
                        flag=false;
                }
            }
        }
        ans=0;
        for(int i=1;i<=n;++i)
            if(!vis[i])
        {
            ext_gcd(M/m[i],m[i],x,y);
            ans+=M/m[i]*x*a[i];
            ans%=M;
        }
        ans=(ans%M+M)%M;
        if(ans==0)
            ans+=M;
        if(flag)
            printf("Case %d: %I64d\n",kk,ans);
        else printf("Case %d: -1\n",kk);
    }
    return 0;
}


你可能感兴趣的:(HDU 3579 中国剩余定理 不互质的情况)