日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

BFS最短路打印路径

發(fā)布時(shí)間:2025/4/5 编程问答 18 豆豆
生活随笔 收集整理的這篇文章主要介紹了 BFS最短路打印路径 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

Problem Description

2020級(jí)的新生即將來(lái)USST報(bào)道了,學(xué)校規(guī)定報(bào)道地點(diǎn)定在了516號(hào)的老體育館。

現(xiàn)在為了方便新生報(bào)道,Wiki自我推薦為新生繪制一張校園地圖。地圖功能很簡(jiǎn)單:假設(shè)校園是一張二維的平面圖,大小為n × m,校園的建筑在地圖上用任意字符表示,如果遇到不能前行的障礙物則用字符N表示,設(shè)起點(diǎn)為S,報(bào)道點(diǎn)為G,請(qǐng)你幫助Wiki計(jì)算出最短的報(bào)道距離以及該條最短路徑上的點(diǎn)坐標(biāo)。

如果存在多條的最短報(bào)道路徑,輸出任意一條即可。(假設(shè)可以在地圖“上下左右”四個(gè)方向上行走,且必存在到達(dá)路線)

Input

第一行輸入兩個(gè)正整數(shù)n和m(2 <= n, m <= 100),表示地圖的大小

第二行開(kāi)始輸入n行m列的建筑物字符標(biāo)識(shí)(字符釋義見(jiàn)上述題面)

Output

輸出第一行一個(gè)正整數(shù)ans,表示從起點(diǎn)S到終點(diǎn)G的最短距離

第二行開(kāi)始輸出最短路徑經(jīng)過(guò)的建筑物坐標(biāo)(xi, yi),輸出一個(gè)換一行,起點(diǎn)和終點(diǎn)坐標(biāo)也要輸出!假設(shè)坐標(biāo)原點(diǎn)為(0, 0)

Sample Input:

3 3 S.. NN. G..

Sample Output:

6 0 0 0 1 0 2 1 2 2 2 2 1 2 0

分析
BFS,記錄路徑。
此處使用兩個(gè)數(shù)組px[dx][dy]=x和py[dx][dy]=y來(lái)記錄點(diǎn)(dx,dy)的前面一點(diǎn)(x,y).

#include<iostream> #include<queue> #include<cstring>using namespace std;const int maxn=200;int m,n,t1,t2,d1,d2;//起點(diǎn)和終點(diǎn) char a[maxn][maxn]; bool vis[maxn][maxn];//表示是否訪問(wèn)過(guò) int dis[4][2]={1,0,0,1,-1,0,0,-1};//四個(gè)方向 int len[maxn][maxn];//保存起點(diǎn)到任何點(diǎn)的最小距離 int px[maxn][maxn],py[maxn][maxn];//記錄最短路徑 queue<pair<int,int> > q;void bfs(){q.push(make_pair(t1,t2));vis[t1][t2]=1;while(!q.empty()){int x=q.front().first;int y=q.front().second;q.pop();if(x==d1&&y==d2) return;for(int i=0;i<4;i++){int dx=x+dis[i][0];int dy=y+dis[i][1];if(dx>=0&&dx<m&&dy>=0&&dy<n&&!vis[dx][dy]&&a[dx][dy]!='N'){if(len[dx][dy]>len[x][y]+1)//距離小者更新 {len[dx][dy]=len[x][y]+1;//長(zhǎng)度 q.push(make_pair(dx,dy));//入隊(duì) vis[dx][dy]=1;//訪問(wèn)過(guò) //v.push_back(make_pair(dx,dy));//保存路徑 px[dx][dy]=x;py[dx][dy]=y;//前一個(gè)坐標(biāo) } }} } }void print(int x,int y){if(x!=-1&&y!=-1){//遞歸出口,到達(dá)起點(diǎn) print(px[x][y],py[x][y]);//如果把遞歸放后面,則是倒序輸出 if(x==d1&&y==d2) cout<<x<<" "<<y;//不能輸出多余的換行符 else cout<<x<<" "<<y<<endl;}}int main(){memset(len,0x3f,sizeof(len));//距離無(wú)窮大 memset(vis,0,sizeof(vis));//表示沒(méi)訪問(wèn)過(guò) memset(px,-1,sizeof(px));memset(py,-1,sizeof(py));cin>>n>>m;for(int i=0;i<n;i++)for(int j=0;j<m;j++){cin>>a[i][j]; if(a[i][j]=='S')t1=i,t2=j;//起點(diǎn) if(a[i][j]=='G')d1=i,d2=j;//終點(diǎn) }len[t1][t2]=0;//起點(diǎn)距離為0 bfs(); cout<<len[d1][d2]<<endl;print(d1,d2);}

遞歸打印的寫(xiě)法
從終點(diǎn)到起點(diǎn)print(d1,d2),由于棧的后進(jìn)先出特性,遞歸最后的先返回,于是正好是先返回起點(diǎn),依次到終點(diǎn)。

void print(int x,int y){if(x!=-1&&y!=-1){//遞歸出口,到達(dá)起點(diǎn) print(px[x][y],py[x][y]);//如果把遞歸放后面,則是倒序輸出 if(x==d1&&y==d2) cout<<x<<" "<<y;//不能輸出多余的換行符 else cout<<x<<" "<<y<<endl;}}

總結(jié)

以上是生活随笔為你收集整理的BFS最短路打印路径的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。