【HDOJ 4272】 LianLianKan (vector深搜+剪枝)

【HDOJ 4272】 LianLianKan

不造正规做法 不过好歹是按题意做的(读懂题有时候也不是好事TOT 据说好多随意连水果去的。。。

经过5小时推出来了……整场就做了这么一道OOOOOOOOOOOTZ 题意要求只能连与他相距小于6的

即最远连到下面除顶部本身外的五个中的一个 有可以发现如果有连续的连其中任意一个效果都是一样的

这样搜索策略就是看下面五个中不连续的然后挨个接着搜。。。各种姿势都试了 各种超时 就这个可以有。。。不过不知道时不时也因为数据水TOT


代码如下:


#include <iostream>
#include <algorithm>
#include <cstring>
#include <cstdio>
#include <queue>
#include <map>
#include <list>
#include <stack>
#include <vector>
#include <set>
#include <ctime>
#include <cmath>
#include <bitset>

using namespace std;
#define STD_REOPEN() freopen("../in.in","r",stdin)
#define STT_REOPEN() freopen("../in.in","w",stdout)
#define INF 0x3f3f3f3f
#define _INF 63
#define eps 1e-4
#define ll long long
#define sc "%lld"
#define pr pair<int,int>
#define mod
#define sz

using namespace std;

vector <int> v;
int n;

bool dfs(vector<int>::iterator pos,int cnt)
{
	if(cnt == n) return true;
	int i,x = 0,np,nnp;
	int data = *pos;

	vector<int>::iterator it;
	vector<int>::iterator tmp;
	v.erase(pos);
	it = pos;
	tmp = it;
	for(x = 0,++it; tmp != v.end() && x < 5; ++tmp,++x,++it)//往下找5个
	{
		if(data == *tmp && (x == 4 || it == v.end() || *it != data))//如果该处和栈顶相同 并且是第五个 或者容器最后一个 或者与下一个不一样(即是连续的最后一个元素
		{
			v.erase(tmp);//深搜
			if(dfs(pos,cnt+2)) return true;
			v.insert(tmp,data);
		}
	}

	v.insert(pos,data);
	return false;
}

int main()
{
	int i,x;
    while(~scanf("%d",&n))
	{
		v.clear();
		for(i = 0; i < n; ++i)
		{
			scanf("%d",&x);
			v.insert(v.begin(),x);//用容器模拟栈(由于容器有删除的方法)
		}
		if(n&1)//奇数个肯定练不完
		{
			puts("0");
			continue;
		}

		if(dfs(v.begin(),0)) puts("1");
		else puts("0");
	}
    return 0;
}


你可能感兴趣的:(DFS+剪枝)