OPJ2.5基本算法之搜索200:Solitaire

OPJ2.5基本算法之搜索200:Solitaire

题目传送门
看网上的题解有点少,我就来 写一篇博客,给有需要的宝宝们
思路:八维数组!同时搜四个点!干就完了!虽然OPJ的数据水,但还是要有一些阴间卡内存的,具体看代码。
AC代码:

#include<bits/stdc++.h>
using namespace std;
bool vis[8][8][8][8][8][8][8][8];
int g[10][10];
int fx[][2]={1,0,-1,0,0,1,0,-1};
struct node 
{
	int x[4],y[4];
	int step;
}s,e;
bool check(node a) 
{   
	for(int i=0;i<4;i++) 
		if(!g[a.x[i]][a.y[i]])return 0;
	return 1;
}
bool judge(node a) 
{  
	for(int i=0;i<4;i++)
		if(a.x[i]<0||a.x[i]>=8||a.y[i]<0||a.y[i]>=8)return 1;
	if(vis[a.x[0]][a.y[0]][a.x[1]][a.y[1]][a.x[2]][a.y[2]][a.x[3]][a.y[3]])return 1;
	return 0;
}
bool empty(node a, int k) 
{  
	for(int i=0;i<4;i++)
		if(i!=k&&a.x[i]==a.x[k]&&a.y[i]==a.y[k])return 0;
	return 1;
}
bool bfs() 
{
	memset(vis, 0, sizeof vis);
	queue<node>q;
	node a,b;
	a.step=0;
	for(int i=0;i<4;i++) 
	{
		a.x[i]=s.x[i];
		a.y[i]=s.y[i];
	}
	q.push(a);
	vis[a.x[0]][a.y[0]][a.x[1]][a.y[1]][a.x[2]][a.y[2]][a.x[3]][a.y[3]]=1;
	while(!q.empty()) 
	{
		a=q.front();q.pop();
		if(a.step>=8)return 0;
		if(check(a))return 1;
		for(int i=0;i<4;i++)
			for(int j=0;j<4;j++) 
			{
				b=a;
				b.x[i]+=fx[j][0];b.y[i]+=fx[j][1];
				b.step++;
				if(judge(b))continue;
				if(empty(b,i)) 
				{ 
					if(check(b))return 1;
					vis[b.x[0]][b.y[0]][b.x[1]][b.y[1]][b.x[2]][b.y[2]][b.x[3]][b.y[3]]=1;
					q.push(b);
				}
				else
				{ 
					b.x[i]+=fx[j][0];b.y[i]+=fx[j][1];
					if(judge(b)||!empty(b,i))continue;
					if(check(b))return 1;
					vis[b.x[0]][b.y[0]][b.x[1]][b.y[1]][b.x[2]][b.y[2]][b.x[3]][b.y[3]]=1;
					q.push(b);
				}
			}
	}
	return 0;
}
int main() 
{
	while(cin>>s.x[0]>>s.y[0]) 
	{
		s.x[0]--;s.y[0]--;//卡内存*1
		for(int i=1;i<4;i++) 
		{
			cin>>s.x[i]>>s.y[i];
			s.x[i]--;s.y[i]--;卡内存*2
		}
		memset(g,0,sizeof g);
		for(int i=0;i<4;i++) 
		{
			cin>>e.x[i]>>e.y[i];
			e.x[i]--;e.y[i]--;卡内存*3
			g[e.x[i]][e.y[i]]=1;
		}
		bool flag=bfs();
		if(flag)cout <<"YES"<<endl;
		else cout<<"NO"<<endl;
	}
	return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值