2 1 0 0 1 6 -100 0 90 -50 0 1 -20 0 1 100 0 90 47 0 1 23 0 1
Alice Bob
所有的圆之间构成一棵数的关系,然后就是树上的删边博弈.
建树可以扫描线,然后暴力出奇迹~
#include <bits/stdc++.h> using namespace std; #define maxn 41111 #define eps 1e-8 struct circle { double x, y, r; bool operator < (const circle &a) const { return r < a.r; } }p[maxn]; int n; int cnt = 0; struct node { int u, v, next; }edge[maxn*4]; int tot, head[maxn], fa[maxn]; bool in (int i, int j) {//判断圆i是不是在j中 double xx = p[i].x-p[j].x; double yy = p[i].y-p[j].y; return xx*xx+yy*yy <= p[j].r*p[j].r; } void add_edge (int u, int v) { edge[tot].u = u, edge[tot].v = v, edge[tot].next = head[u], head[u] = tot++; } int dfs (int u) { int ans = 0; for (int i = head[u]; i != -1; i = edge[i].next) { int v = edge[i].v; ans ^= (dfs (v)+1); } return ans; } int main () { //freopen ("in.txt", "r", stdin); int t; scanf ("%d", &t); while (t--) { scanf ("%d", &n); memset (head, -1, sizeof head); for (int i = 0; i < n; i++) fa[i] = i; tot = cnt = 0; for (int i = 0; i < n; i++) { scanf ("%lf%lf%lf", &p[i].x, &p[i].y, &p[i].r); } sort (p, p+n); for (int i = 0; i < n; i++) { for (int j = i+1; j < n; j++) { if (in (i, j)) { fa[i] = j; add_edge (j, i); break; } } } int ans = 0; for (int i = 0; i < n; i++) if (fa[i] == i) { ans ^= (dfs (i)+1); } printf ("%s\n", ans ? "Alice" : "Bob"); } return 0; }