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

歡迎訪問 生活随笔!

生活随笔

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

编程问答

hdu 1429 胜利大逃亡(续) bfs+状态压缩

發(fā)布時(shí)間:2024/10/6 编程问答 29 豆豆
生活随笔 收集整理的這篇文章主要介紹了 hdu 1429 胜利大逃亡(续) bfs+状态压缩 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

勝利大逃亡(續(xù))

Time Limit: 4000/2000 MS (Java/Others)????Memory Limit: 65536/32768 K (Java/Others)
Total Submission(s): 10137????Accepted Submission(s): 3664


Problem Description Ignatius再次被魔王抓走了(搞不懂他咋這么討魔王喜歡)……

這次魔王汲取了上次的教訓(xùn),把Ignatius關(guān)在一個(gè)n*m的地牢里,并在地牢的某些地方安裝了帶鎖的門,鑰匙藏在地牢另外的某些地方。剛開始Ignatius被關(guān)在(sx,sy)的位置,離開地牢的門在(ex,ey)的位置。Ignatius每分鐘只能從一個(gè)坐標(biāo)走到相鄰四個(gè)坐標(biāo)中的其中一個(gè)。魔王每t分鐘回地牢視察一次,若發(fā)現(xiàn)Ignatius不在原位置便把他拎回去。經(jīng)過若干次的嘗試,Ignatius已畫出整個(gè)地牢的地圖。現(xiàn)在請(qǐng)你幫他計(jì)算能否再次成功逃亡。只要在魔王下次視察之前走到出口就算離開地牢,如果魔王回來的時(shí)候剛好走到出口或還未到出口都算逃亡失敗。

Input 每組測試數(shù)據(jù)的第一行有三個(gè)整數(shù)n,m,t(2<=n,m<=20,t>0)。接下來的n行m列為地牢的地圖,其中包括:

. 代表路
* 代表墻
@ 代表Ignatius的起始位置
^ 代表地牢的出口
A-J 代表帶鎖的門,對(duì)應(yīng)的鑰匙分別為a-j
a-j 代表鑰匙,對(duì)應(yīng)的門分別為A-J

每組測試數(shù)據(jù)之間有一個(gè)空行。

Output 針對(duì)每組測試數(shù)據(jù),如果可以成功逃亡,請(qǐng)輸出需要多少分鐘才能離開,如果不能則輸出-1。

Sample Input 4 5 17 @A.B. a*.*. *..*^ c..b* 4 5 16 @A.B. a*.*. *..*^ c..b*
Sample Output 16 -1
Author LL
Source ACM暑期集訓(xùn)隊(duì)練習(xí)賽(三)
Recommend linle

思路:

1.因?yàn)橛?0種不同的鑰匙,每種都有兩種狀態(tài),結(jié)合二進(jìn)制的特點(diǎn),
剛好把這10把鑰匙當(dāng)成每一個(gè)位,要 1<<10 個(gè)位保存所有的狀態(tài)


2.模擬撿起鑰匙,撿起鑰匙就是說明這個(gè)位上的數(shù)字變成1狀態(tài)
所以想到位運(yùn)算 |,改變這個(gè)點(diǎn)的狀態(tài)


3.模擬碰到門的情況,就和這個(gè)位置上的位&一次,

結(jié)果是1代表有鑰匙,可以開門?

#include<cstdio> #include<iostream> #include<algorithm> #include<cstring> #include<queue> using namespace std; const int maxn=20+10; char map[maxn][maxn]; int n,m,t; bool vis[maxn][maxn][(1<<10)+10]; //狀態(tài)壓縮,最多有10種鑰匙 int dx[]={-1,1,0,0}; int dy[]={0,0,-1,1}; struct Point {int x,y,step;int key; }; queue<Point>Q; Point st; bool check(int x,int y) {if(x>=1&&x<=n&&y>=1&&y<=m&&map[x][y]!='*')return true;return false; } int bfs() {while(!Q.empty()) Q.pop();memset(vis,false,sizeof(vis));vis[st.x][st.y][st.key]=true;st.key=st.step=0;Q.push(st);Point cur,nex;while(!Q.empty()){cur=Q.front();Q.pop();if(map[cur.x][cur.y]=='^')return cur.step;for(int i=0;i<4;i++){nex.x=cur.x+dx[i];nex.y=cur.y+dy[i];nex.key=cur.key;if(check(nex.x,nex.y)){nex.step=cur.step+1;if(nex.step>=t)continue;else if(map[nex.x][nex.y]>='A'&&map[nex.x][nex.y]<='Z'){int temp=map[nex.x][nex.y]-'A';//int nk=cur.key&(1<<temp);int nk=cur.key&1<<temp;//先左移,后與運(yùn)算 if(nk&&!vis[nex.x][nex.y][nex.key]){vis[nex.x][nex.y][nex.key]=true;Q.push(nex);}}else if(map[nex.x][nex.y]>='a'&&map[nex.x][nex.y]<='z'){int temp=map[nex.x][nex.y]-'a';//nex.key=cur.key|(1<<temp);nex.key=cur.key|1<<temp;//先左移,后或運(yùn)算 if(!vis[nex.x][nex.y][nex.key]){vis[nex.x][nex.y][nex.key]=true;Q.push(nex);}}else{if(!vis[nex.x][nex.y][nex.key]){vis[nex.x][nex.y][nex.key]=true;Q.push(nex);}}//else}//if}//for}return -1; } inline void read_graph() {char str[maxn];for(int i=1;i<=n;i++){scanf("%s",str+1);for(int j=1;j<=m;j++){if(str[j]=='@'){st.x=i;st.y=j;map[i][j]=str[j];}else map[i][j]=str[j];} } } int main() {while(~scanf("%d%d%d",&n,&m,&t)){read_graph();int ans=bfs();printf("%d\n",ans);}return 0; }

總結(jié)

以上是生活随笔為你收集整理的hdu 1429 胜利大逃亡(续) bfs+状态压缩的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

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