Analysis
(先吐槽一下自己,AC了好几个月才写题解,题目都忘了……) 一道数论方面的题目(话说那时似乎往dp那儿想了很久啊……)。考虑x和y两个数,ax+by能够组成gcd(x,y)的所有倍数。推广到n个数的情形就是a[1]*x[1]+a[2]*x[2]+...+a[n]*x[n]能够组成x[1],x[2],...,x[n]的最大公约数的任意倍数。那么题目中A和X两个数列,由于X是未知的数列,所以应用上述结论,求出A[1],A[2],...,A[n]的最大公约数,然后利用扩展欧几里德解个方程逆着推回去就可以了。
Accepted Code
var
t,a,x:array[0..110] of longint;
n,p,b,i,k,r,s:longint;
function ex_gcd(x,y:longint;var a,b:longint):longint;
begin
if y=0 then
begin
a:=1;
b:=0;
ex_gcd:=x;
exit;
end;
ex_gcd:=ex_gcd(y,x mod y,b,a);
b:=b-x div y*a;
end;
begin
readln(n,p,b);
for i:=1 to n do
begin
read(a[i]);
a[i]:=a[i] mod p;
if a[i]=0 then
a[i]:=p;
end;
t[1]:=a[1];
for i:=2 to n do
t[i]:=ex_gcd(t[i-1],a[i],r,s);
for k:=0 to p-1 do
if t[n]*k mod p=b then
break;
if t[n]*k mod p=b then
begin
writeln('YES');
for i:=n downto 2 do
begin
s:=ex_gcd(t[i-1],a[i],r,x[i]);
x[i]:=x[i]*k mod p;
k:=r*k mod p;
if k=0 then
k:=p;
end;
x[1]:=k;
for i:=1 to n do
while x[i]<0 do
inc(x[i],p);
for i:=1 to n-1 do
write(x[i],' ');
writeln(x[n]);
end
else
writeln('NO');
end.