[数论]青蛙的约会

Luogu原题

可以看出是同余方程。青蛙A起点为x,速度为m;青蛙B起点为y,速度为n。那么他们相遇用式子表示就是:
x + km ≡ y + kn (mod l)
因为题目要解k,因此变换一下:(m - n)k ≡ y - x (mod l)
这题m、n、y、x、l已知,因此就是求解线性同余方程 ax ≡ c (mod b)最小整数解x

扩欧求解。

有些细节, 已经标注。

#include <iostream>
#include <cmath>
using namespace std;

#define LL long long

LL x, y, m, n, L;
LL k, ans;

void Extended_gcd(LL a, LL b, LL &x, LL &y, LL &d) {
    if(b == 0) {
        x = 1, y = 0, d = a;
        return;
    }
    Extended_gcd(b, a%b, y, x, d);
    y -= x*(a/b);
}

LL Linear_Equation(LL a, LL c, LL b) {
    LL x, y, d;
    Extended_gcd(a, b, x, y, d);
    if(c % d != 0) return -1e8;
    x *= c/d;
    b /= d; //重要:约掉gcd 
    return ((x % b) + b) % b;
}

int main() {
    cin >> x >> y >> m >> n >> L;
    if(m < n) swap(m, n), swap(x, y); //保证m-n>0
    ans = Linear_Equation(m-n, (((y-x)%L)+L)%L, L); //y-x可能是负数,变正并取模 
    if(ans == -1e8) { //无解 
        cout << "Impossible" << endl;
        return 0;
    }
    cout << ans << endl;
    return 0;
}

猜你喜欢

转载自blog.csdn.net/Binary_Heap/article/details/79318402
今日推荐