编程刷题-P1746 离开中山路 BFS/最短路径
P1746 离开中山路
题目背景
《爱与愁的故事第三弹·shopping》最终章。
题目描述
爱与愁大神买完东西后,打算坐车离开中山路。现在爱与愁大神在 x1,y1x_1,y_1x1,y1 处,车站在 x2,y2x_2,y_2x2,y2 处。现在给出一个 n×n(n≤1000)n \times n(n \le 1000)n×n(n≤1000) 的地图,000 表示马路,111 表示店铺(不能从店铺穿过),爱与愁大神只能垂直或水平着在马路上行进。爱与愁大神为了节省时间,他要求最短到达目的地距离(每两个相邻坐标间距离为 111)。你能帮他解决吗?
输入格式
第 111 行包含一个数 nnn。
第 222 行到第 n+1n+1n+1 行:整个地图描述(000 表示马路,111 表示店铺,注意两个数之间没有空格)。
第 n+2n+2n+2 行:四个数 x1,y1,x2,y2x_1,y_1,x_2,y_2x1,y1,x2,y2。
输出格式
只有 111 行,即最短到达目的地距离。
输入输出样例 #1
输入 #1
3
001
101
100
1 1 3 3
输出 #1
4
说明/提示
对于 20%20\%20% 数据,满足 1≤n≤1001\leq n \le 1001≤n≤100。
对于 100%100\%100% 数据,满足 1≤n≤10001\leq n \le 10001≤n≤1000。
代码
(1)定义Node结点
(2)创建队列q
(3)首先将起点插入队列,push()
(4)取出队列头结点,删除头结点,然后遍历四个方向,计算新结点满足 不出界 、没有被访问过 、值为0 的条件后,将新结点插入队列,更新距离数组,或者直接更新vis数组。
(5)最后输出vis[x2][y2]-1。 //注意需要减去1,因为起点多算了一个1。
注:不要将变量名设为y1,会报错。
#include <bits/stdc++.h>
using namespace std;
struct Node{int x,y;
};
int n,x1,yy1,x2,yy2;
char c;
int mmap[1001][1001];
int vis[1001][1001];
queue<Node> qq;
int dir[4][2]={{0,1},{0,-1},{1,0},{-1,0}};
void bfs(int x,int y){vis[x][y]=1;qq.push((Node){x,y});while(!qq.empty()){int xx=qq.front().x;int yy=qq.front().y;qq.pop();for(int i=0;i<4;i++){int xxx=xx+dir[i][0];int yyy=yy+dir[i][1];if(xxx>1&&yyy>1&&xxx<=n&&yyy<=n&&(mmap[xxx][yyy]==0)&&(vis[xxx][yyy]==0)){qq.push((Node){xxx,yyy});vis[xxx][yyy]=vis[xx][yy]+1;}}}
}
int main(){cin>>n;for(int i=1;i<=n;i++){for(int j=1;j<=n;j++){cin>>c;if(c=='0') mmap[i][j]=0;else mmap[i][j]=1;}}cin>>x1>>yy1>>x2>>yy2;bfs(x1,yy1);cout<<vis[x2][yy2]-1<<endl;return 0;
}