我自己想了个嵌套的队列,就像是嵌套循环来枚举一样
有多少个起点,每个起点可以走五步,如果能走到4这个点,则4这个点又可以作为起点,加入外层队列
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
#include <stdio.h>
#include <string.h>
#include <queue>
using namespace std;
struct node
{
int x,y,step;
}a;
int n,m,ans,map[9][9],tmp[9][9],used[9][9];
void bfs()
{
queue<node> p;
p.push(a);
int i,cnt,row,col,dir[4][2]={-1,0,1,0,0,-1,0,1};
while (!p.empty())
{
memcpy(tmp,map,sizeof(tmp));
a=p.front();p.pop();
used[a.x][a.y]=1;
tmp[a.x][a.y]=0;
cnt=a.step;
a.step=0;
queue<node> q;
q.push(a);
while (!q.empty())
{
a=q.front();q.pop();
if(a.step==5)break;
for (i=0;i<4;i++)
{
row=a.x+dir[i][0];
col=a.y+dir[i][1];
if (row<n&&col<m&&row>=0&&col>=0&&tmp[row][col]!=0)
{
node b;
b.x=row;
b.y=col;
b.step=a.step+1;
if(tmp[row][col]==3)
{
if(b.step+cnt<ans)ans=a.step+cnt;
break;
}
if(tmp[row][col]==4&&!used[row][col])
{
b.step+=cnt;
p.push(b);
}
if(tmp[row][col]==1)q.push(b);
tmp[row][col]=0;
}
}
}
}
}
int main()
{
int T,i,j,x,y;
scanf("%d",&T);
while (T--)
{
scanf("%d%d",&n,&m);
for (i=0;i<n;i++)
{
for(j=0;j<m;j++)
{
scanf("%d",&map[i][j]);
if(map[i][j]==2)
{
x=i;y=j;
}
}
}
a.x=x;
a.y=y;
a.step=0;
ans=0x3f3f3f3f;
memset(used,0,sizeof(used));
bfs();
if(ans!=0x3f3f3f3f)printf("%d\n",ans+1);
else printf("-1\n");
}
return 0;
}