hdu 1198 Farm Irrigation(并查集)

http://acm.hdu.edu.cn/showproblem.php?pid=1198

原来看解题报告做过的一道题,现在拾起来再做感觉还是有点难度,慢慢想想也就思路清晰了。首先发现通道只要相碰就能连接。结构体记录是否能够连接,把能连接的用并查集归为同一集合,不能连接的则属于不同的集合。最后统计几何数就欧了。。、

View Code
#include <cstdio>
#include <cstring>
#define MAXN 59
struct node
{
int up;
int down;
int left;
int right;
};
node tagp[11]=
{
{1,0,1,0},{1,0,0,1},
{0,1,1,0},{0,1,0,1},
{1,1,0,0},{0,0,1,1},
{1,0,1,1},{1,1,1,0},
{0,1,1,1},{1,1,0,1},
{1,1,1,1}
};//记录是否连接情况1代表连接,0代表不行
int f[MAXN*MAXN];
void init()
{
for (int i = 0; i < MAXN*MAXN;i++)
{
f[i] = i;
}
}
int find(int x)
{
if(x != f[x])
f[x] = find(f[x]);
return f[x];
}
void Union(int x,int y)
{
x = find(x);
y = find(y);
if(x != y)
f[y]=x;
}
int main()
{
char str[MAXN][MAXN];
int n,m,i,j;
int x,y;
while (scanf("%d%d",&n,&m))
{
init();
if(n == -1&&m == -1)
break;
for (i = 0; i < n; ++i)
scanf("%s",str[i]);
int a,b,c;
//从头一直检查右边以及下边即可
for (i = 0; i < n; ++i)
{
for (j = 0; j < m; ++j)
{
a = str[i][j] - 'A';
b = str[i][j+1] - 'A';
c = str[i+1][j] - 'A';
if(j+1<m)//边界考虑
{
if(tagp[a].right&&tagp[b].left)
{
x = i*m+j;
y = i*m+j+1;
Union(x,y);
}
}
if(i+1<n)//边界考虑
{
if(tagp[a].down&&tagp[c].up)
{
x = i*m+j;
y = (i+1)*m+j;
Union(x,y);
}
}
}
}
int count = 0;
int pos;
for (i = 0; i < n; ++i)
{
for (j = 0; j < m; ++j)
{
pos = i*m+j;
if(pos == find(pos))
count++;
}
}
printf("%d\n",count);
}
return 0;
}


 

posted @ 2012-02-07 19:26  E_star  阅读(185)  评论(0编辑  收藏  举报