E. Two Labyrinths(双图BFS)

E. Two Labyrinths

time limit per test

2.0 s

memory limit per test

256 MB

input

standard input

output

standard output

A labyrinth is the rectangular grid, each of the cells of which is either free or wall, and it's possible to move only between free cells sharing a side.

Constantine and Mike are the world leaders of composing the labyrinths. Each of them has just composed one labyrinth of size n × m, and now they are blaming each other for the plagiarism. They consider that the plagiarism takes place if there exists such a path from the upper-left cell to the lower-right cell that is the shortest for both labyrinths. Resolve their conflict and say if the plagiarism took place.

Input

In the first line two integers n and m (1 ≤ n, m ≤ 500) are written — the height and the width of the labyrinths.

In the next n lines the labyrinth composed by Constantine is written. Each of these n lines consists of m characters. Each character is equal either to «#», which denotes a wall, or to «.», which denotes a free cell.

The next line is empty, and in the next n lines the labyrinth composed by Mike is written in the same format. It is guaranteed that the upper-left and the lower-right cells of both labyrinths are free.

Output

Output «YES» if there exists such a path from the upper-left to the lower-right cell that is the shortest for both labyrinths. Otherwise output «NO».

Examples

input

Copy

3 5
.....
.#.#.
.....
  

.....
#.#.#
.....

output

Copy

NO

input

Copy

3 5
.....
.#.##
.....
  

.....
##.#.
.....

output

Copy

YES

题目连接:

http://codeforces.com/gym/100187/problem/E

#include <cstdio>
#include <cstring>
#include <queue>
using namespace std;
char map[2][510][510];//存两个地图
int visit[2][510][510];//为防止破坏map地图而设置的记录方位的路径变
int cnt[2];//统计两张地图的最短步数
int dirx[4]={-1,1,0,0};
int diry[4]={0,0,-1,1};
int n,m;
int flag;
struct Node
{
	int x,y,step;
};
queue<Node> q;
int cheak(struct Node x,int k)
{
	if(x.x>=0&&x.x<n&&x.y>=0&&x.y<m&&(map[k][x.x][x.y]=='.'&&visit[k][x.x][x.y]==0))
	{
		return 1;
	}
	else
	{
		return 0;
	}
}
void bfs(int k)     //该题是一定存在最短路的
{
	while(!q.empty())    //多次数据时的队列清空
	{
		q.pop();
	}
	visit[k][0][0]=1;
	Node a,b;
	a.x=0,a.y=0,a.step=1;
	q.push(a);
	while(!q.empty())
	{
		a=q.front();
		q.pop();
		if(a.x==n-1&&a.y==m-1)
		{
            cnt[k]=min(cnt[k],a.step);
		}
		for(int i=0;i<4;i++)
		{
			b.x=a.x+dirx[i];
			b.y=a.y+diry[i];
			if(cheak(b,k))//判断下一个点是否可走
			{
				b.step=a.step+1;
				visit[k][b.x][b.y]=1;
				q.push(b);
			}
		}
	}
}
void bbfs(int k)  //走两个图的bfs,妙
{
	while(!q.empty())
	{
		q.pop();
	}                //清空栈的操作
	visit[k][0][0]=1;
	Node a,b;
	a.x=0,a.y=0,a.step=1;
	q.push(a);
	while(!q.empty())
	{
		a=q.front();
		q.pop();
		if(a.x==n-1&&a.y==m-1)
		{
			if(cnt[k]==a.step)
			{
				flag=1;
				break;//广搜的特点是一旦到达目的地,那么一定是最短路
			}
		}
		for(int i=0;i<4;i++)
		{
			b.x=a.x+dirx[i];
			b.y=a.y+diry[i];
			if(cheak(b,k)&&map[0][b.x][b.y]=='.'&&map[1][b.x][b.y]=='.')//两个图都能走,妙
			{
				b.step=a.step+1;
				visit[k][b.x][b.y]=1;
				q.push(b);
			}
		}
	}
}
int main()
{
	scanf("%d%d",&n,&m);
	for(int i=0;i<n;i++)
	{
		scanf("%s",map[0][i]);
	}
	for(int i=0;i<n;i++)
	{
		scanf("%s",map[1][i]);
	}
	cnt[0]=0x3f3f3f3f;
	cnt[1]=0x3f3f3f3f;
	memset(visit,0,sizeof(visit));
	bfs(0);
	bfs(1);
	if(cnt[0]!=cnt[1])//如果各自的最短路的步数都不一样,那么肯定不是一张抄袭的图
	{
		printf("NO\n");
		return 0;
	}
	memset(visit,0,sizeof(visit));
	flag=0;
	bbfs(0);//两张图一起搜
	if(flag==1)
	{
		printf("YES\n");
	}
	else
	{
		printf("NO\n");
	}
	return 0;
}

 

阅读更多
个人分类: c++ 广搜
上一篇HDU-1016 Prime Ring Problem(素数环)
下一篇HDU-6377 度度熊看球赛(正向dp)
想对作者说点什么? 我来说一句

没有更多推荐了,返回首页

关闭
关闭
关闭