这道题主要就是如何处理转弯的次数问题,我们可以这样做,把初始转弯次数初始化为-1,然后每次进行四个方向的搜索的时候,转弯次数加一,并且在这一转弯次数之下往4个方向笔直地走(因为直走的话转弯次数不变),把走过的路标记一下,这样,我们就可以确保走到哪个地方,都是使用了最少的转弯次数。这道题的状态表示很简单,就是坐标和转弯次数
typedef struct node{
int x,y;
int dir;
};<span style="white-space:pre"> </span>
然后就是要注意输入,包括空格的处理<pre name="code" class="cpp">for(int i=0;i<n;i++)
for(int j=0;j<m;j++)
scanf(" %c",&map[i][j]);
然注意看题目
scanf("%d%d%d%d%d",&turn,&sy,&sx,&ey,&ex);
(发现什么了吗?)
具体看代码:<pre name="code" class="cpp">#include<stdio.h>
#include<stdlib.h>
#include<iostream>
using namespace std;
#include <queue>
#define maxn 105
char map[maxn][maxn];
int vis[maxn][maxn];
int n,m;
int sx,sy,ex,ey,turn;
int d[4][2]={0,1,1,0,-1,0,0,-1};
typedef struct node{
int x,y;
int dir;
};
node temp,s,next1;
int bfs()
{
queue<node>que;
que.push(s);
while(!que.empty())
{
temp=que.front();
que.pop();
for(int i=0;i<4;i++)
{
int x1=temp.x;
int y1=temp.y;
while(1)
{
next1.dir=temp.dir+1;
x1+=d[i][0];
y1+=d[i][1];
if(x1<0||x1>=n||y1<0||y1>=m||map[x1][y1]=='*')
break;
if(vis[x1][y1]) continue; //要先判定,再标记,不然x1可能为-1,数组越界
vis[x1][y1]=1;
next1.x=x1;
next1.y=y1;
if(x1==ex&&y1==ey&&next1.dir<=turn) return 1;//转弯次数要在这里判断,WA了好多次,不可以在出队的时候判断,因为这时候可能转弯次数已经超了
que.push(next1);
}
}
}
return 0;
}
int main()
{
int kace;
scanf("%d",&kace);
while(kace--)
{
scanf("%d%d",&n,&m);
for(int i=0;i<n;i++)
for(int j=0;j<m;j++)
scanf(" %c",&map[i][j]);
scanf("%d%d%d%d%d",&turn,&sy,&sx,&ey,&ex);
if(sx==ex&&sy==ey)
{
printf("yes\n");
continue;
}
sx--;//从0开始的话记得要全部减一
sy--;
ex--;
ey--;
memset(vis,0,sizeof(vis));
vis[sx][sy]=1;
s.dir=-1;
s.x=sx;
s.y=sy;
if(bfs())
printf("yes\n");
else
printf("no\n");
}
return 0;
}