救援(信息学奥赛一本通-T1073)

序言:

没有学好搜索,板子题不会打呜呜呜~
我来简要说一说。


题目描述:

铁塔尼号遇险了!他发出了求救信号。距离最近的哥伦比亚号收到了讯息,时间就是生命,必须尽快 赶到那里。

通过侦测,哥伦比亚号获取了一张海洋图。这张图将海洋部分分化成 n*n 个比较小的单位,其中用 1 标明的是陆地,用 0 标明是海洋。船只能从一个格子,移到相邻的四个格子。

为了尽快赶到出事地点,哥伦比亚号最少需要走多远的距离。

输入格式:

第一行为 n,下面是一个 n*n 的 0、1 矩阵,表示海洋地图。
最后一行为四个小于 n 的整数,分别表示哥伦比亚号和铁塔尼号的位置。

输出格式:

哥伦比亚号到铁塔尼号的最短距离,答案精确到整数。

样例输入:

3
001
101
100
1 1 3 3

样例输出:

4

数据范围与提示:

1 < = n < = 1000 1 <= n <= 1000 1<=n<=1000

题目分析:

我只想说水题只怪我,上课不认真,划水去了。。。

这道题这需要确定四个方位,然后

一个BFS,记录并更新答案。

并把答案压入队里。之后就没有了。。。


题解:

#include <bits/stdc++.h>

using namespace std;

const int MAXN = 1005;
int mp[MAXN][MAXN]; 
int n; 
struct node {
    
    
	int x, y; // 坐标 
};
bool vis[MAXN][MAXN]; // 判断当前位置是否走过 
int dx[5] = {
    
    0, 1, 0, -1};
int dy[5] = {
    
    1, 0, -1, 0}; // 四个方向 
node st, ed;
int ans[MAXN][MAXN]; // ans[i][j]表示到(i,j)需要的最短路程 

void bfs() {
    
     
	queue<node> q;
	q.push(st);  
	vis[st.x][st.y] = true; 
	while(!q.empty()) {
    
      
		node cur = q.front();
		q.pop();
		for(int i = 0; i < 4; i++) {
    
      
			int cx = cur.x + dx[i];
			int cy = cur.y + dy[i];
			if(cx < 1 || cx > n) continue;
			if(cy < 1 || cy > n) continue;
			if(vis[cx][cy] == false && mp[cx][cy] == 0) {
    
    
				// 如果没走过,且为海洋 
				vis[cx][cy] = true; // 标记下一个点为走过 
				node nxt;
				nxt.x = cx;
				nxt.y = cy;
				ans[nxt.x][nxt.y] = ans[cur.x][cur.y] + 1;  // 更新
				if(nxt.x == ed.x && nxt.y == ed.y) {
    
     
				// 如果下一个点就是终点直接输出 
					printf("%d", ans[ed.x][ed.y]);
					return ;
				} 
				q.push(nxt); // 入队 
			}
		}
	}
	return ;
}

int main() {
    
    
	scanf ("%d", &n);
	for(int i = 1; i <= n; i++) {
    
    
		char s[MAXN];
		scanf ("%s", s + 1);
		for(int j = 1; j <= n; j++) 
			mp[i][j] = s[j] - '0';
	}
	scanf ("%d %d %d %d", &st.x, &st.y, &ed.x, &ed.y);
	bfs();
	return 0; 
}

猜你喜欢

转载自blog.csdn.net/C202207LYX/article/details/107727374
今日推荐