sgu 140

有点小难的数论问题哦。。
aX=b(mod n)很好求吧。。
怎么才能把这个问题化成这种呢?
首先序列A可以mod P。。
因为a和b可以组成gcd(a,b)的任何倍数。。反之也是。。
因为可以用扩展欧几里得算出ax+by=gcd(a,b)嘛。。
故可以把a和b换成gcd(a,b)。。。
然后就一个个处理。。
若k是之前的所有数的gcd。。当前处理t。。
得出kx+ty=gcd(k,t)。。
那么之前所有数的系数全部*x(然后再modP)。。t的系数就是y
就可以使系数没有问题了。。
无解就是gcd(all包括n)无法整除b。。
然后直接输出系数就可以了。。
P.S为了方便可以把P也带入方程写成…..+PXn+1=b..
Code。。。
#include<stdio.h>
#include<iostream>
using namespace std;
const int maxn=200;
long long N,P,B;
long long A[maxn];
long long X[maxn];
long long gcd(long long a,long long b)
{
while(b){int t=a;a=b;b=t%b;}
return a;
}
void get(long long a,long long b,long long&x,long long&y)
{
if(b==0)
{
x=1;y=0;
return;
}
get(b,a%b,y,x);
y-=(a/b)*x;
}
int main()
{
cin>>N>>P>>B;
cin>>A[0];long long k=A[0];
for(int i=1;i<N;i++)
{
cin>>A[i];   
A[i]%=P;
k=gcd(k,A[i]);
}
A[N]=P;
k=gcd(k,A[N]);
if(B%k!=0)
{
cout<<"NO"<<endl;
return 0;
}   
k=gcd(A[0],A[1]);
get(A[0],A[1],X[0],X[1]);
for(int i=2;i<=N;i++)
{
long long x;
get(k,A[i],x,X[i]);
for(int j=0;j<i;j++)
{
X[j]*=x;
X[j]%=P;
while(X[j]<0)
X[j]+=P;
}
k=gcd(k,A[i]);
}
cout<<"YES"<<endl;
for(int i=0;i<N;i++)
{
X[i]*=(B/k);
X[i]%=P;
while(X[i]<0) X[i]+=P;
cout<<X[i]<<" ";
}
}

Leave a Reply

Your email address will not be published. Required fields are marked *