格子游戏x(并查集)

格子游戏

【问题描述】
  Alice和Bob玩了一个古老的游戏:首先画一个n * n的点阵(下图n = 3)   接着,他们两个轮流在相邻的点之间画上红边和蓝边:
 
 
 
    直到围成一个封闭的圈(面积不必为1)为止,“封圈”的那个人就是赢家。因为棋盘实在是太大了(n <= 200),他们的游戏实在是太长了!他们甚至在游戏中都不知道谁赢得了游戏。于是请你写一个程序,帮助他们计算他们是否结束了游戏?
【输入格式】
  输入数据第一行为两个整数n和m。m表示一共画了m条线。以后m行,每行首先有两个数字(x, y),代表了画线的起点坐标,接着用空格隔开一个字符,假如字符是"D ",则是向下连一条边,如果是"R "就是向右连一条边。输入数据不会有重复的边且保证正确。
【输出格式】
  输出一行:在第几步的时候结束。假如m步之后也没有结束,则输出一行“draw”。
【输入样例】
  3 5
  1 1 D
  1 1 R
  1 2 D
  2 1 R
  2 2 D
【输出样例】
  4
 
 1 #include<iostream>
 2 #include<cstdio>
 3 #define Maxn 2002
 4 
 5 using namespace std;
 6 
 7 int n,m;
 8 
 9 struct zuobiao{
10     int x,y;
11 }zb[Maxn][Maxn],f1,f2;
12 
13 zuobiao gz(zuobiao q)
14 {
15     if(zb[q.x][q.y].x==q.x&&zb[q.x][q.y].y==q.y) return q;
16     zb[q.x][q.y]=gz(zb[q.x][q.y]);
17     return zb[q.x][q.y];
18 }
19 int main()
20 {
21     int x,y;
22     char zifu;
23     scanf("%d%d",&n,&m);
24     for(int i=1;i<=n;i++)//初始化操作 
25     {
26         for(int j=1;j<=n;j++)
27         {
28             zb[i][j].x=i;
29             zb[i][j].y=j;
30         }
31     }
32     for(int i=1;i<=m;i++)
33     {
34         cin>>x>>y>>zifu;
35         if(zifu=='D')//down
36         {
37             f1=gz(zb[x][y]);
38             f2=gz(zb[x+1][y]);
39         } 
40         if(zifu=='R')//right
41         {
42             f1=gz(zb[x][y]);
43             f2=gz(zb[x][y+1]);
44         }
45         if(f1.x==f2.x&&f1.y==f2.y)
46         {
47             cout<<i<<endl;
48             return 0;
49         }
50         else zb[f1.x][f1.y]=f2;
51     }
52     cout<<"draw"<<endl;
53     return 0;
54  } 

 

posted @ 2017-04-12 19:15  夜雨声不烦  阅读(493)  评论(0编辑  收藏  举报