【bfs】神殿(jzoj 2296)
神殿
jzoj 2296
題目大意:
用一個(gè)n?mn*mn?m的矩陣,每個(gè)單位都是一個(gè)1?11*11?1的房間,房間的四個(gè)方向只有某些方向有門(說(shuō)明如下圖),要從一個(gè)房間走向相鄰的房間(算一個(gè)單位時(shí)間)必須要他們中間的兩個(gè)門都是存在,也可以把所有房間的門順時(shí)針旋轉(zhuǎn)一輪(算一個(gè)單位時(shí)間),現(xiàn)在問從(x1,y1)(x_1,y_1)(x1?,y1?)走到(x2,y2)(x_2,y_2)(x2?,y2?)最少需要多少各單位時(shí)間
輸入樣例#1
2 2 +* *U 1 1 2 2輸出樣例#1
-1輸入樣例#2
2 3 <>< ><> 1 1 2 1輸出樣例#2
4數(shù)據(jù)范圍
對(duì)于30%的數(shù)據(jù),滿足n,m?10n,m \leqslant 10n,m?10。
對(duì)于50%的數(shù)據(jù),滿足n,m?50n,m \leqslant 50n,m?50。
對(duì)于另外20%的數(shù)據(jù),滿足沒一個(gè)房間要么只有一個(gè)方向沒門,要么一個(gè)方向上的門都沒有。
對(duì)于100%的數(shù)據(jù),滿足n,m?1000n,m \leqslant 1000n,m?1000。
注
題目標(biāo)中的特殊符號(hào):
<>^v+*|-解題思路:
直接bfs去跑,每一次要么旋轉(zhuǎn),要么走,這樣時(shí)間復(fù)雜度就是o(4nm)o(4nm)o(4nm)(整個(gè)圖加上旋轉(zhuǎn)的四種情況)
代碼:
#include<queue> #include<cstdio> #include<cstring> #include<iostream> using namespace std; const int dx[4]={-1,0,1,0}; const int dy[4]={0,-1,0,1}; int n,m,x1,x2,y1,y2,a[1500][1500][5],p[1500][1500][5]; char x; struct rec {int x,y,r,num; }; void input()//輸入 {scanf("%d %d",&n,&m);for (int i=1;i<=n;++i){getchar();for (int j=1;j<=m;++j){x=getchar();if (x=='+') a[i][j][0]=1,a[i][j][1]=1,a[i][j][2]=1,a[i][j][3]=1;//判斷每一種情況else if (x=='-') a[i][j][1]=1,a[i][j][3]=1;else if (x=='|') a[i][j][0]=1,a[i][j][2]=1;else if (x=='^') a[i][j][0]=1;else if (x=='>') a[i][j][3]=1;else if (x=='<') a[i][j][1]=1;else if (x=='v') a[i][j][2]=1;else if (x=='L') a[i][j][0]=1,a[i][j][2]=1,a[i][j][3]=1;else if (x=='R') a[i][j][0]=1,a[i][j][1]=1,a[i][j][2]=1;else if (x=='U') a[i][j][1]=1,a[i][j][2]=1,a[i][j][3]=1;else if (x=='D') a[i][j][0]=1,a[i][j][1]=1,a[i][j][3]=1;}}scanf("%d %d %d %d",&x1,&y1,&x2,&y2); } bool check(rec gg,int f) {if (!p[gg.x+dx[f]][gg.y+dy[f]][gg.r])//判斷是否到過if (a[gg.x][gg.y][(f+gg.r)%4] && a[gg.x+dx[f]][gg.y+dy[f]][(f+gg.r+2)%4])//判斷是否兩道門都開if(gg.x+dx[f]>0 && gg.x+dx[f]<=n && gg.y+dy[f]>0 && gg.y+dy[f]<=m)//判斷是否超界return true;return false; } void bfs() {queue<rec>d;rec o;o.x=x1;o.y=y1;o.num=0;//時(shí)間o.r=0;//旋轉(zhuǎn)次數(shù)d.push(o);p[x1][y1][0]=1;if (o.x==x2&&o.y==y2){printf("0");return;}while(!d.empty()){rec h=d.front();d.pop();if (!p[h.x][h.y][(h.r+1)%4])//旋轉(zhuǎn){rec o;o.x=h.x;o.y=h.y;o.num=h.num+1;o.r=(h.r+1)%4;p[o.x][o.y][o.r]=1;d.push(o);}for (int i=0;i<4;++i)//往某個(gè)方向走if (check(h,i)){rec o;o.x=h.x+dx[i];o.y=h.y+dy[i];o.r=h.r;o.num=h.num+1;p[o.x][o.y][o.r]=1;d.push(o);if (o.x==x2&&o.y==y2){printf("%d",o.num);return;}}}printf("-1"); } int main() {input();bfs(); }總結(jié)
以上是生活随笔為你收集整理的【bfs】神殿(jzoj 2296)的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 【ST表】栈(jzoj 2295)
- 下一篇: Linux重启网卡的方法