http://poj.org/problem?id=2236
思路:用set保存已修好的电脑(使用set是为了去重),每次修电脑p时就把set中的与p距离<=d的电脑合并。
完整代码:
/*766ms,640KB*/
#include<cstdio>
#include<set>
using namespace std;
int x[1005], y[1005];
int fa[1005], rk[1005];
bool vis[1005];
int find(int x) {return fa[x] = (fa[x] == x ? x : find(fa[x]));}
void merge(int x, int y)
{
x = find(x), y = find(y);
if (x == y) return;
if (rk[x] < rk[y]) fa[x] = y;
else
{
fa[y] = x;
if (rk[x] == rk[y]) ++rk[x];
}
}
int main()
{
int n, d, i, j, p, q;
char ch;
scanf("%d%d", &n, &d);
d *= d;
for (i = 1; i <= n; ++i) fa[i] = i;
for (i = 1; i <= n; ++i) scanf("%d%d", &x[i], &y[i]);
getchar();
set<int> id;
set<int>::iterator iter;
while (~(ch = getchar()))
{
if (ch == 'O')
{
scanf("%d", &p);
vis[p] = true;
id.insert(p);
for (iter = id.begin(); iter != id.end(); ++iter)
{
j = *iter;
if (vis[j] && (x[p] - x[j]) * (x[p] - x[j]) + (y[p] - y[j]) * (y[p] - y[j]) <= d)
merge(p, j);
}
}
else
{
scanf("%d%d", &p, &q);
puts(find(p) == find(q) ? "SUCCESS" : "FAIL");
}
getchar();
}
return 0;
}