欧几里得算法与扩展欧几里得算法

欧几里得算法
已知a和b,求出\(gcd(a,b)\)
时间复杂度\(O(\log n)\)
\(gcd(a,b)*lcm(a,b)=a*b\)

int gcd(int a,int b){
    return b==0?a:gcd(b,a%b);
}

//优化
int gcd(int a,int b){
    if(a==0) return b;
    if(b==0) return a;
    if(a==b) return a;
    if(a>b) return gcd(a%b,b);
    return gcd(a,b%a);
}

模板题:hdu2104 hide handkerchief
扩展欧几里得算法
求出所有的x,y,使得对于给定的a,b,满足\(ax+by=c\)
时间复杂度\(O(\log n)\)
当且仅当\(gcd(a,b)|c\)时,存在整数解x,y
所以exgcd可以求解方程\(ax+by=gcd(a,b)\)
\(bx_1+(a\%b)y_1=gcd(b,a\%b)\)
\(bx_1+(a-b\lfloor\frac{a}{b}\rfloor)y_1=gcd(a,b)\)
\(ay_1+b(x_1-\lfloor\frac{a}{b}\rfloor y_1)=gcd(a,b)\)
所以原方程中,\(\left\{\begin{aligned}x=y_1\\y=x_1-\lfloor\frac{a}{b}\rfloor y_1\end{aligned}\right.\)。通过递归求出\(x_1,y_1\),可以得到x,y
原方程的解集:\(\{(x,y)|x=x_1+k*b/gcd(a,b),y=y_1-k*a/gcd(a,b),k\in z\}\)

void exgcd(int a,int b,int& x,int& y){
    if(!b) {y=0;x=1;return;}
    exgcd(b,a%b,y,x);
    y-=a/b*x;
}

模板题:hdu2669 Romantic

posted @ 2020-07-10 00:58  fxq1304  阅读(80)  评论(0编辑  收藏  举报