n*m的球桌的(x,y)点上有一个球,给球任意八个方向的初速度问球能否进洞,并把洞口坐标输出
主要是很难想到补边,以及用exgcd求出的交点坐标不一定是第一个交点,甚至有可能是另一个方向的交点,这个有点难处理
#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>
using namespace std;
typedef __int64 ll;
int n, m, x, y, vx, vy;
ll ans_x, ans_y;
ll exgcd(ll a, ll b, ll &x, ll &y) {
if (b == 0) {x = 1; y = 0;return a;}
ll d, t;
d = exgcd(b, a % b, x, y);
t = x - a/b*y; x = y; y = t;
return d;
}
int solve() {
if (vx*vy == 0) {
if (vx == 0) {
if (x == 0 || x == n) {
if (vy == 1) {ans_x = x; ans_y = m;}
else {ans_x = x; ans_y = 0;}
return true;
}
else return false;
}
if (vy == 0) {
if (y == 0 || y == m) {
if (vx == 1) {ans_x = n; ans_y = y;}
else {ans_x = 0; ans_y = y;}
return true;
}
else return false;
}
}
ll k = vx*vy; ll c = y - k*x;
ll X, Y;
ll d = exgcd(m, -k*n, X, Y);
if (c % d) return false;
ll tmpx = c / d * X;
ll r = -k*n / d;
r = r < 0 ? -r : r;
tmpx = (tmpx % r + r) % r;
if (vy > 0 && tmpx == 0) tmpx = r;
if (vy < 0 && tmpx > 0) {
tmpx = (tmpx - (tmpx/r+1)*r) % r;
}
ll tmpy = (c - m*tmpx) / n;
if (tmpx % 2 != 0) ans_y = m;
else ans_y = 0;
if (tmpy % 2 != 0) ans_x = n;
else ans_x = 0;
return true;
}
int main() {
scanf("%d%d%d%d%d%d",&n,&m,&x,&y,&vx,&vy);
if (!solve()) puts("-1");
else printf("%I64d %I64d\n", ans_x, ans_y);
return 0;
}