生活随笔
收集整理的這篇文章主要介紹了
HDU1026 Ignatius and the Princess I(深度优先搜索)
小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.
2018-5-2
其實(shí)廣搜還是比較容易想到的,但是這道題目相對(duì)復(fù)雜了一點(diǎn),需要注意的是:
1)我們可能在那點(diǎn)需要花個(gè)時(shí)間打個(gè)怪獸
2)我們需要記錄走過(guò)的路徑并倒序輸出(倒序輸出可以用深度優(yōu)先搜索實(shí)現(xiàn))
#include<iostream>
#include<cstring>
#include<queue>
#define inf 0x3f3f3f3f
using namespace std;
const int N =
100;
char x[N+
1][N+
1];
int rx[N*N+
1],ry[N*N+
1];
int m,n;
int dx[
4]={-
1,
1,
0,
0},dy[
4]={
0,
0,-
1,
1};
struct pre{
int p,q;
int a,b;
int c;
}y[N+
1][N+
1];
bool isvalid(
int i,
int j){
if (i<
0||j<
0||i>n-
1||j>m-
1)
return false;
return true;
}
void display(){
if (y[n-
1][m-
1].c==inf){
cout<<
"God please help our poor hero."<<endl;}
else{
cout<<
"It takes "<<y[n-
1][m-
1].c<<
" seconds to reach the target position, let me show you the way."<<endl;
int x1=n-
1,x2=m-
1,i=
1,j;rx[
0]=x1;ry[
0]=x2;
while (!(x1==
0&&x2==
0)){rx[i]=y[x1][x2].p;ry[i]=y[x1][x2].q;x1=rx[i];x2=ry[i];i++;}
int t=
1,pp;
for (j=i-
1;j>=
0;j--){
if (x[rx[j]][ry[j]]==
'.'||x[rx[j]][ry[j]]==
'X') {
if (j-
1>=
0)
cout<<t<<
"s:("<<rx[j]<<
","<<ry[j]<<
")->"<<
"("<<rx[j-
1]<<
","<<ry[j-
1]<<
")"<<endl;t++;}
else{pp=x[rx[j]][ry[j]]-
'0';
while (pp){
cout<<t<<
"s:FIGHT AT ("<<rx[j]<<
","<<ry[j]<<
")"<<endl;t++;pp--;}
if (j-
1>=
0)
cout<<t<<
"s:("<<rx[j]<<
","<<ry[j]<<
")->"<<
"("<<rx[j-
1]<<
","<<ry[j-
1]<<
")"<<endl;t++;}}}
cout<<
"FINISH"<<endl;
}
void init(){
for (
int i=
0;i<n;i++){
for (
int j=
0;j<m;j++){y[i][j].c=inf;y[i][j].a=i;y[i][j].b=j;}}
}
void bfs(){init();
int k,ii,jj;
queue<struct pre>que;
struct pre tmp;tmp.p=
0;tmp.q=
0;tmp.a=
0;tmp.b=
0;tmp.c=
0;que.push(tmp);
while (!que.empty()){tmp=que.front();que.pop();
for (k=
0;k<
4;k++){ii=tmp.a+dx[k];jj=tmp.b+dy[k];
if (isvalid(ii,jj)&&x[ii][jj]!=
'X'){
if (x[ii][jj]==
'.'){
if (tmp.c+
1<y[ii][jj].c){y[ii][jj].c=tmp.c+
1;y[ii][jj].p=tmp.a;y[ii][jj].q=tmp.b;que.push(y[ii][jj]);}}
else{
if (tmp.c+x[ii][jj]-
'0'+
1<y[ii][jj].c){y[ii][jj].c=tmp.c+x[ii][jj]-
'0'+
1;y[ii][jj].p=tmp.a;y[ii][jj].q=tmp.b;que.push(y[ii][jj]); }}}}}display();
}
int main(){
int i,j;
while (
cin>>n>>m){
for (i=
0;i<n;i++){
for (j=
0;j<m;j++){
cin>>x[i][j];}}bfs();}
return 0;
}
說(shuō)一下我的思路:與平時(shí)的bfs不同的是,之前只要搜到即是結(jié)果,因?yàn)槲覀兊韧谡业綄訑?shù)最少的,但是這里還可以需要加上打怪獸的時(shí)間,我看好多都是用優(yōu)先隊(duì)列實(shí)現(xiàn)的;還有一個(gè),之前的而言,走過(guò)了就不能再走了,但是這里可以還可能往回走,因?yàn)槲矣涗浟说矫恳粋€(gè)點(diǎn)所需要的最小值,如果用flag數(shù)組標(biāo)記的話,那么我們就無(wú)法更新到達(dá)某一個(gè)點(diǎn)的花費(fèi)的最小值了,這里解決的方案是:我們?cè)诩尤腙?duì)列時(shí),只有當(dāng)當(dāng)前節(jié)點(diǎn)被重新更新了,我們才將它放在隊(duì)列中。反之,我們就沒(méi)有必要加入進(jìn)去了。
算法結(jié)束時(shí),我們記錄的是最短路前驅(qū)。
新人創(chuàng)作打卡挑戰(zhàn)賽發(fā)博客就能抽獎(jiǎng)!定制產(chǎn)品紅包拿不停!
總結(jié)
以上是生活随笔為你收集整理的HDU1026 Ignatius and the Princess I(深度优先搜索)的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。