1. 程式人生 > >hdu 1728 逃離迷宮 bfs記步數

hdu 1728 逃離迷宮 bfs記步數

gree inpu math.h .cn miss tle new efi tro

題鏈:http://acm.hdu.edu.cn/showproblem.php?pid=1728

逃離迷宮

Time Limit: 1000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 18702 Accepted Submission(s): 4526


Problem Description   給定一個m × n (m行, n列)的迷宮,迷宮中有兩個位置,gloria想從迷宮的一個位置走到另外一個位置,當然迷宮中有些地方是空地,gloria能夠穿越,有些地方是障礙,她必須繞行。從迷宮的一個位置。僅僅能走到與它相鄰的4個位置中,當然在行走過程中,gloria不能走到迷宮外面去。令人頭痛的是,gloria是個沒什麽方向感的人,因此,她在行走過程中,不能轉太多彎了,否則她會暈倒的。我們假定給定的兩個位置都是空地,初始時。gloria所面向的方向未定,她能夠選擇4個方向的不論什麽一個出發,而不算成一次轉彎。gloria能從一個位置走到另外一個位置嗎?
Input   第1行為一個整數t (1 ≤ t ≤ 100),表示測試數據的個數。接下來為t組測試數據,每組測試數據中,
  第1行為兩個整數m, n (1 ≤ m, n ≤ 100),分別表示迷宮的行數和列數,接下來m行。每行包含n個字符,當中字符‘.‘表示該位置為空地,字符‘*‘表示該位置為障礙。輸入數據中僅僅有這兩種字符。每組測試數據的最後一行為5個整數k, x1
, y1, x2, y2 (1 ≤ k ≤ 10, 1 ≤ x1, x2 ≤ n, 1 ≤ y1, y2 ≤ m),當中k表示gloria最多能轉的彎數。(x1, y1), (x2, y2)表示兩個位置,當中x1,x2相應列。y1, y2相應行。



Output   每組測試數據相應為一行,若gloria能從一個位置走到另外一個位置。輸出“yes”,否則輸出“no”。
Sample Input

2
5 5
...**
*.**.
.....
.....
*....
1 1 1 1 3
5 5
...**
*.**.
.....
.....
*....
2 1 1 1 3

Sample Output
no
yes



做法:每次走一個方向就一直走究竟,路徑上假設沒訪問過的點,就入隊。由於是bfs。每次轉向數僅僅添加1,所以最先訪問,就是轉向數最少的。

入隊點假設再直走或者後退,那都是會訪問已經訪問的點,是沒意義的。所以必會轉向,所以轉向數是+1的。

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <limits.h>
#include <malloc.h>
#include <ctype.h>
#include <math.h>
#include <string>
#include <iostream>
#include <algorithm>
using namespace std;
#include <stack>
#include <queue>
#include <vector>
#include <deque>
#include <set>
#include <map>
#define INF 999999999
#define eps 0.00001
#define LL __int64
#define pi acos(-1.0)
  
struct point
{
	int x,y;
	int step;//記錄轉彎數。
};
int vis[110][110];
int n,m;
int dir[4][2]={
	1,0,
	-1,0,
	0,1,
	0,-1
};

char mp[110][110];
int ok(point nw)
{
	if(nw.x>=0&&nw.x<n&&nw.y>=0&&nw.y<m&&mp[nw.x][nw.y]=='.')
		return 1;
	return 0;
}
int sx,sy,ex,ey;

int bfs()
{
	memset(vis,0,sizeof vis);
	point sta,nw,nex; 
	sta.x=sx;
	sta.y=sy;
	sta.step=-1;//第一次不算轉彎
	queue<point>q;
	q.push(sta);
	while(!q.empty())
	{
		nw=q.front();
		if(nw.x==ex&&nw.y==ey)
			return max(0,nw.step);
		q.pop(); 
		for(int i=0;i<4;i++)
		{
			nex=nw;
			nex.x+=dir[i][0];
			nex.y+=dir[i][1];
			nex.step=nw.step+1;//由於是走到了盡頭了。所以每一次
			//每次step僅僅加1,所以能夠用bool vis
			while(ok(nex))
			{ 
				if(vis[nex.x][nex.y]==0)
				{
					q.push(nex);
					vis[nex.x][nex.y]=1;//停在這個點。
				}  
				nex.x+=dir[i][0];
				nex.y+=dir[i][1]; 
			}  
		}
	}
	return 999999;
}
int main()
{
	int t;
	scanf("%d",&t);
	while(t--)
	{
		scanf("%d%d",&n,&m);
		for(int i=0;i<n;i++)
			scanf("%s",mp[i]);
		int k;
		scanf("%d%d%d%d%d",&k,&sy,&sx,&ey,&ex);
		sy--,sx--,ey--,ex--; 
		int ans=bfs();
		if(k>=ans)
			printf("yes\n");
		else
			printf("no\n");
	}
	return 0;
}
/*
2
5 5
...**
*.**.
.....
.....
*....
1 1 1 1 3
5 5
...**
*.**.
.....
.....
*....
2 1 1 1 3 
*/





hdu 1728 逃離迷宮 bfs記步數