2021寒假_菜菜子编程日志

偷偷过蓝桥

2018_08题
最近在学BFS 别骂了别骂了,知道错了,正在赶进度
所以看到这题套用了正在学的BFS模板
顺便用我那并不充足的知识库添了一些算法

结果……答案出来了
时间也超了

//经典的BFS问题
#include<stdio.h>
#include<queue>
#include<string.h>
using namespace std;
const int maxn=1006;
int n;//地图大小 
//位置 
struct Point{
	int x,y;
}point;
//01矩阵
char map[maxn][maxn];
int cmap[maxn][maxn];
//记录是否入过队 
bool inq[maxn][maxn]={false};
//方向:
int dx[4]={0,0,1,-1};
int dy[4]={1,-1,0,0};
//判断坐标是否需要被访问 
bool judge(int x,int y){
	if(x<=0||x>n||y<=0||y>n)return false;//越界
	if(inq[x][y])return false;//访问过了
	if(map[x][y]=='.')return false;//是海
	return true;	
} 
//BFS广度优先搜索 
void bfs(int x,int y){
	queue<Point>Q;//定义队列
	point.x=x,point.y=y;//当前结点坐标(x,y)
	Q.push(point);//将结点point入队
	inq[x][y]=true;//将(x,y)设置成已入过队
	while(!Q.empty()) {
		Point top=Q.front();//取出队首元素
		Q.pop();//队首元素出队
		for(int i=0;i<4;i++){
			int newX=top.x+dx[i];
			int newY=top.y+dy[i];
			if(judge(newX,newY)){//如果位置需要访问 
				point.x=newX;
				point.y=newY;
				Q.push(point);//新位置入队
				inq[newX][newY]=true;//设置新位置已经入过队 
			}
		} 
	}
}
//全球变暖
void change(){
	int x,y;
	for(int i=1;i<=n;i++)
		for(int j=1;j<=n;j++){
			for(int k=0;k<4;k++){
				x=i+dx[k];
				y=j+dy[k];
				if(cmap[x][y]==0){//如果靠近海,则消失 
					map[i][j]='.';
					break;
				}
			}
		}
} 
int main(){
	while(scanf("%d",&n)!=EOF){
		memset(cmap,0,sizeof(cmap));
		for(int i=1;i<=n;i++){ 
		    getchar();//自动过滤掉每行后的换行符 
			for(int j=1;j<=n;j++){ 
				scanf("%c",&map[i][j]);
				if(map[i][j]=='#')cmap[i][j]=1;
				else cmap[i][j]=0;
			}
		} 
		int ans=0;
		for(int i=1;i<=n;i++){
			for(int j=1;j<=n;j++){
				if(map[i][j]=='#'&&inq[i][j]==false){
					ans++;
					bfs(i,j);
				}
				
			}
		}
		//printf("%d\n",ans);//测试 
		memset(inq,false,sizeof(inq));
		int ans1=0;
		change();
		for(int i=1;i<=n;i++){
			for(int j=1;j<=n;j++){
				if(map[i][j]=='#'&&inq[i][j]==false){
					ans1++;
					bfs(i,j);
				}
				
			}
		}
	//	printf("%d\n",ans1);//测试 
/*	for(int i=1;i<=n;i++)
	{
		for(int j=1;j<=n;j++){
			printf("%c",map[i][j]);
		}
		printf("\n");
	}*/
	printf("%d\n",ans-ans1);
	}	
	return 0;
} 

正确答案在这里:
大佬的答案

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值