题目链接
题意
小明来到一个由n x m个格子组成的迷宫,有些格子是陷阱,用’#‘表示,小明进入陷阱就会死亡,’.'表示没有陷阱。小明所在的位置用’S’表示,目的地用’T’表示。
小明只能向上下左右相邻的格子移动,每移动一次花费1秒。
有q个单向传送阵,每个传送阵各有一个入口和一个出口,入口和出口都在迷宫的格子里,当走到或被传送到一个有传送阵入口的格子时,小明可以选择是否开启传送阵。如果开启传送阵,小明就会被传送到出口对应的格子里,这个过程会花费3秒;如果不开启传送阵,将不会发生任何事情,小明可以继续向上下左右四个方向移动。
一个格子可能既有多个入口,又有多个出口,小明可以选择任意一个入口开启传送阵。使用传送阵是非常危险的,因为有的传送阵的出口在陷阱里,如果小明使用这样的传送阵,那他就会死亡。也有一些传送阵的入口在陷阱里,这样的传送阵是没有用的,因为小明不能活着进入。请告诉小明活着到达目的地的最短时间。
思路
- 带传送带的走迷宫,由于传送带的存在可能使步数无序,可使用优先队列
参考代码
#include<bits/stdc++.h>
using namespace std;
char aa[510][510];
int vis[510][510];
int yd[4][2]= {{1,0},{-1,0},{0,1},{0,-1}};
vector< pair<int, int> > transmit[510][510];
int sx,sy;
struct node
{
int x,y,bs;
node(int _x = 0, int _y = 0, int _bs = 0): x(_x), y(_y), bs(_bs) {}
bool operator < (const node &s) const
{
return bs > s.bs;
}
};
priority_queue<node>q;
int main()
{
int n,m,t;
while(cin>>n>>m>>t)
{
while(!q.empty())
q.pop();
for(int i = 1; i <= n; i++)
{
for(int j = 1; j <= m; j++)
{
transmit[i][j].clear();vis[i][j] = 0;
}
}
for(int i=1; i<=n; i++)
{
for(int j=1; j<=m; j++)
{
cin>>aa[i][j];
if(aa[i][j]=='S')
{
sx=i;
sy=j;
}
}
}
int tmpx1,tmpy1,tmpx2,tmpy2;
for(int i=0; i<t; i++)
{
cin>>tmpx1>>tmpy1>>tmpx2>>tmpy2;
transmit[tmpx1+1][tmpy1+1].push_back({tmpx2+1, tmpy2+1});
}
q.push(node(sx, sy, 0));
for(int i = 0; i < transmit[sx][sy].size(); i++)
{
int xx = transmit[sx][sy][i].first, yy = transmit[sx][sy][i].second;
if(!vis[xx][yy] && aa[xx][yy] != '#' && xx >= 1 && yy <= n && xx >= 1 && yy <= m)
{
q.push(node(xx, yy, 3));
}
}
int fl=0;
while(!q.empty())
{
node tmp=q.top();
q.pop();
if(vis[tmp.x][tmp.y])
continue;
vis[tmp.x][tmp.y] = 1;
if(aa[tmp.x][tmp.y]=='T')
{
fl=1;
cout<<tmp.bs<<endl;
break;
}
int x,y;
for(int i=0; i<4; i++)
{
x=tmp.x+yd[i][0];
y=tmp.y+yd[i][1];
if(x>=1&&x<=n&&y>=1&&y<=m&&vis[x][y]==0&&aa[x][y]!='#')
{
for(int j = 0; j < transmit[x][y].size(); j++)
{
int xx = transmit[x][y][j].first, yy = transmit[x][y][j].second;
if(!vis[xx][yy] && aa[xx][yy] != '#' && xx >= 1 && xx <= n && yy >= 1 && yy <= m)
{
q.push(node(xx, yy, tmp.bs + 4));
}
}
q.push(node(x, y, tmp.bs + 1));
}
}
}
if(fl==0)
cout<<-1<<endl;
}
}