题意:给定正整数 a , b a,b a,b,构造出正整数 c , d , e , f c,d,e,f c,d,e,f,满足 c d − e f = a b , ( d , f < b ) \dfrac{c}{d}-\dfrac{e}{f}=\dfrac{a}{b},(d,fdc−fe=ba,(d,f<b)
思路: e x g c d + exgcd+ exgcd+数论。
p 1 : p 1: p1: a , b a,b a,b不互质时,即 g c d ( a , b ) > 1 gcd(a,b)>1 gcd(a,b)>1。
我们可以构造这样一个式子: a + b b − 1 = a b \dfrac{a+b}{b}-1=\dfrac{a}{b} ba+b−1=ba
令 b ′ = b g , a ′ = a g b'=\dfrac{b}{g},a'=\dfrac{a}{g} b′=gb,a′=ga。
a + b b − 1 = a b = a ′ b ′ \dfrac{a+b}{b}-1=\dfrac{a}{b}=\dfrac{a'}{b'} ba+b−1=ba=b′a′
a + b g = a + b g b g \dfrac{a+b}{g}=\dfrac{\dfrac{a+b}{g}}{\dfrac{b}{g}} ga+b=gbga+b
即 c = a + b g , d = b g , e = f = 1 c=\dfrac{a+b}{g},d=\dfrac{b}{g},e=f=1 c=ga+b,d=gb,e=f=1。
这样能满足 1 ≤ d , f < b 1\leq d,f1≤d,f<b。
p 2 : a , b p2:a,b p2:a,b互质且 b b b质因数的种类只有一个。
这种情况是无解的,因为 d , f < b d,fd,f<b,所以 d , f d,f d,f的分解质因数 p k p_k pk的个数都小于 b b b的 p k p_k pk个数,所以左边 d f df df通分后,分母不可能等于 b b b。
p 3 : p3: p3: a , b a,b a,b互质且 b b b质因数种类不只一个。
显然我们可以构造出互质的两个数 d , f d,f d,f满足 d × f = b d\times f=b d×f=b。
这样有 c f − d e d f = a b \dfrac{cf-de}{df}=\dfrac{a}{b} dfcf−de=ba。
即 c f − d e = a cf-de=a cf−de=a,在 f , d , a f,d,a f,d,a已知下求 c , d c,d c,d,这显然是扩展欧几里得。
且肯定有整数解,因为 d , f d,f d,f互质,说明 g c d ( d , f ) = 1 , 1 ∣ a gcd(d,f)=1,1|a gcd(d,f)=1,1∣a则必定有整数解。
接下来套板子就可以了 ,注意是求正整数解,所以当 c c c为负数时要将其变为正整数。
可能有人会问 c c c为正数时,能不能保证 e e e也是正数呢,当然可以。
因为 f c 1 − d e 1 = 1 fc_1-de_1=1 fc1−de1=1,显然 c 1 c_1 c1为正数,因为 f , d f,d f,d为正数,显然 e 1 e_1 e1为正数。
即: c = c 1 × a , e = e 1 × a c=c_1\times a,e=e_1\times a c=c1×a,e=e1×a都为正数。
#include
using namespace std;
typedef long long ll;
const int N=2e6+5,M=2e4+5,inf=0x3f3f3f3f,mod=1e9+7;
#define mst(a) memset(a,0,sizeof a)
#define lx x<<1
#define rx x<<1|1
#define reg register
#define PII pair
#define fi first
#define se second
#define pb push_back
int a,b,p[N],vis[N],ss[N];
void pre(){
int n=2e6,cnt=0;
ss[1]=1;
for(int i=2;i<=n;i++){
if(!vis[i])
p[cnt++]=i,ss[i]=i;
for(int j=0;j<cnt&&i*p[j]<=n;j++){
vis[i*p[j]]=1,ss[i*p[j]]=p[j];
if(i%p[j]==0) break;
}
}
}
template<class T>
void exgcd(T a,T b,T &x,T &y){
if(!b){
x=1,y=0;
return;
}
exgcd(b,a%b,y,x);
y-=(a/b)*x;
}
int main(){
int t;
pre();
scanf("%d",&t);
while(t--){
scanf("%d%d",&a,&b);
int g=__gcd(a,b);
if(g>1){
printf("%d %d 1 1\n",(a+b)/g,b/g); //不互质.
continue;
}
ll f=b,d=1;
while(b>1&&f%ss[b]==0) f/=ss[b],d*=ss[b];
if(f==b||f==1) puts("-1 -1 -1 -1");
else {
ll c,e;
exgcd(f,d,c,e);
if(c<0)
c=(c%d+d)%d,e=(1-f*c)/d;
c*=a,e*=a;
printf("%lld %lld %lld %lld\n",c,d,-e,f);
}
}
return 0;
}