题意:给你p、q,初始状态(x1, y1),终点状态(x2, y2),每次操作可以是 (+p, +q), (+p, -q) , (-p, +q), (-p, -q), (+q, +p), (+q, -p), (-q, +p), (-q, -p),问初始状态能不能到终点状态。
思路:对于初始状态到终止状态变化了 (x2-x1, y2-y1),设为变化了(A, B) ,得方程 px1 + qy1 = A, px2 + qy2 = B,很容易得知满足x1, y2奇偶情况相同和y1,x2奇偶情况相同就可以。然后只需要算出x,y的相对奇偶情况,比较下就可以了。
坑的是。。。明明FAQ里写64位用long long,为何我改成__int64才过。。。坑了好久啊
code:
#include
#include
#include
using namespace std;
typedef __int64 ll;
ll exgcd(ll a, ll b, ll &x, ll &y) {
if(!b) {
x = 1; y = 0;
return a;
}
ll ret = exgcd(b, a%b, y, x);
y -= a/b*x;
return ret;
}
ll ABS(ll x) {
return x > 0 ? x : -x;
}
int v1[111], v2[111];
bool solve(ll a, ll b, ll N, int f[111]) {
if(a == 0) {
if(b == 0) {
if(!N) {
f[11] = f[22] = f[12] = f[21] = 1;
return true;
}
return false;
}
else {
if(N%b == 0) {
if((N/b) & 1) f[11] = f[21] = 1;
else f[12] = f[22] = 1;
return true;
}
return false;
}
}
else if(b == 0) {
if(N%a == 0) {
if((N/a) & 1) f[12] = f[11] = 1;
else f[22] = f[21] = 1;
return true;
}
return false;
}
ll x, y, d = exgcd(a, b, x, y);
if(!N) {
a /= d; b /= d;
int w = (b&1) ? 1 : 2, e = (a&1) ? 1 : 2;
f[w*10+e] = 1;
f[22] = 1;
return true;
}
if(N % d) return false;
x *= N/d; y *= N/d;
int w = (x&1) ? 1 : 2, e = (y&1) ? 1 : 2;
f[w*10+e] = 1;
x += b/d; y -= a/d;
w = (x&1) ? 1 : 2, e = (y&1) ? 1 : 2;
f[w*10+e] = 1;
return true;
}
int main() {
ll p, q, x1, x2, y1, y2;
scanf("%I64d%I64d%I64d%I64d%I64d%I64d", &p, &q, &x1, &y1, &x2, &y2);
if(p < 0) p = -p;
if(q < 0) q = -q;
ll A = x2-x1, B = y2-y1;
if(A < 0) A = -A;
if(B < 0) B = -B;
if(!solve(p, q, A, v1) || !solve(p, q, B, v2)) puts("NO");
else {
//printf("v1 11 = %d 12 = %d 21 = %d 22 = %d\n", v1[11], v1[12], v1[21], v1[22]);
//printf("v2 11 = %d 12 = %d 21 = %d 22 = %d\n", v2[11], v2[12], v2[21], v2[22]);
if((v1[11] && v2[11]) || (v1[12] && v2[21]) || (v1[21] && v2[12]) || (v1[22] && v2[22])) puts("YES");
else puts("NO");
}
return 0;
}