链接:点击打开链接
题意:给你A~K这样的田地,蓝色的线相当于水管,用这些田地组成n*m的距形,需要多少个输水点才可以把这些田地全灌溉。其实也就是查有几个不连通的集合。
思路:用并查集,DFS,BFS都可以,我是用BFS,我是把有水管的一边用1标记,没有用0标记,每次把没有访问过的田地,且和上一个田地有连接的加入队列,进行BFS,每次访问过的做好标记。做了几次BFS,就需要几个输水点。
其中出现一个错误,a[4][2]={-1,0,1,0,0,-1,0,1},我理解的是左右上下,但其实是上下左右,我也不知道这是为什么,求大牛解释。就因为这里我的bfs函数的判断写错,改了这里就A啦。所以以后还是x坐标一个数组,y坐标一个数组,分开写,这样保险一些。。。。
#include<iostream>
#include<cstdio>
#include<cstring>
#include<queue>
using namespace std;
struct node{
int l,r,d,u;
}q[55][55];
struct nd{
int l,r,d,u,xx,yy;
};
int n,m,a[4][2]={-1,0,1,0,0,-1,0,1};
char str[55][55];
int vis[55][55];
void bfs(int x,int y){
int i;
queue<nd>Q;
nd pp,qq;
pp.xx=x;
pp.yy=y;
pp.l=q[x][y].l;
pp.r=q[x][y].r;
pp.d=q[x][y].d;
pp.u=q[x][y].u;
vis[x][y]=1;
Q.push(pp);
while(!Q.empty()){
pp=Q.front();
Q.pop();
for(i=0;i<4;i++){
//qq=pp;
qq.xx=pp.xx+a[i][0];
qq.yy=pp.yy+a[i][1];
if(qq.xx>0&&qq.xx<=n&&qq.yy>0&&qq.yy<=m&&vis[qq.xx][qq.yy]==0){
qq.l=q[qq.xx][qq.yy].l;
qq.r=q[qq.xx][qq.yy].r;
qq.d=q[qq.xx][qq.yy].d;
qq.u=q[qq.xx][qq.yy].u;
if(i==0&&pp.u==1&&qq.d==1){
vis[qq.xx][qq.yy]=1;
Q.push(qq);
}
else if(i==1&&pp.d==1&&qq.u==1){
vis[qq.xx][qq.yy]=1;
Q.push(qq);
}
else if(i==2&&pp.l==1&&qq.r==1){
vis[qq.xx][qq.yy]=1;
Q.push(qq);
}
else if(i==3&&pp.r==1&&qq.l==1){
vis[qq.xx][qq.yy]=1;
Q.push(qq);
}
}
}
}
}
int main(){
int i,j,sum;
while(~scanf("%d %d",&n,&m)){
if(n==-1&&m==-1)
break;
for(i=1;i<=n;i++){
getchar();
for(j=1;j<=m;j++){
scanf("%c",&str[i][j]);
if(str[i][j]=='A'){
q[i][j].l=1;
q[i][j].r=0;
q[i][j].u=1;
q[i][j].d=0;
}
else if(str[i][j]=='B'){
q[i][j].l=0;
q[i][j].r=1;
q[i][j].u=1;
q[i][j].d=0;
}
else if(str[i][j]=='C'){
q[i][j].l=1;
q[i][j].r=0;
q[i][j].u=0;
q[i][j].d=1;
}
else if(str[i][j]=='D'){
q[i][j].l=0;
q[i][j].r=1;
q[i][j].u=0;
q[i][j].d=1;
}
else if(str[i][j]=='E'){
q[i][j].l=0;
q[i][j].r=0;
q[i][j].u=1;
q[i][j].d=1;
}
else if(str[i][j]=='F'){
q[i][j].l=1;
q[i][j].r=1;
q[i][j].u=0;
q[i][j].d=0;
}
else if(str[i][j]=='G'){
q[i][j].l=1;
q[i][j].r=1;
q[i][j].u=1;
q[i][j].d=0;
}
else if(str[i][j]=='H'){
q[i][j].l=1;
q[i][j].r=0;
q[i][j].u=1;
q[i][j].d=1;
}
else if(str[i][j]=='I'){
q[i][j].l=1;
q[i][j].r=1;
q[i][j].u=0;
q[i][j].d=1;
}
else if(str[i][j]=='J'){
q[i][j].l=0;
q[i][j].r=1;
q[i][j].u=1;
q[i][j].d=1;
}
else if(str[i][j]=='K'){
q[i][j].l=1;
q[i][j].r=1;
q[i][j].u=1;
q[i][j].d=1;
}
}
}
memset(vis,0,sizeof(vis));
sum=0;
for(i=1;i<=n;i++)
for(j=1;j<=m;j++){
if(vis[i][j]==0){
bfs(i,j);
sum++;
}
}
printf("%d\n",sum);
}
return 0;
}