pku_2034_Anti-prime Sequences

一道不錯的搜索入門題.

題目大意:

http://poj.org/problem?id=2034

給你三個數,n,m,d 要求從n到m之間的n-m+1個數組成一個序列,有如下特點:

1.連續2-d個數的合不能爲素數

2.若沒有這樣的序列,輸出

No anti-prime sequence exists.
如樣例2:

1,3,5,4,6,2,10,8,7,9
其中: 3,5,4   5,4,6  6,2,10 等等均不爲素數,10,8   8,7 等也不爲素數

解題思路:

因爲d只有10,暴力DFS搜索,最壞爲1000*10*10.先打10000的素數表.

搜索方式,對每一位枚舉,同時由rec函數判定,這個數與其連續後d個數的合是否素數.剪枝方面沒什麼好的方法~


源代碼:

#include <myhead>
const int M=10011;
const int N=1001;
int n,m,d,num;
bool _hash[N],prim_hash[M];
int result[N];

void prim()
{
	memset(prim_hash,0,sizeof(prim_hash));
	prim_hash[0]=prim_hash[1]=true;
	for(int i=2;i<=100;++i) {
		if(!prim_hash[i]) {
			for(int j=i+i;j<M;j+=i)
				prim_hash[j]=true;
		}
	}
}

inline bool rec(int index,int value)
{
	if(index==0)
		return true;
	int left=index-d+1;
	left=max(left,0);
	for(int i=index-1;i>=left;--i) {
		value+=result[i];
		if(!prim_hash[value])
			return false;
	}
	return true;
}

bool dfs(int index)
{
	if(index==num)
		return true;
	for(int i=n;i<=m;++i) {
		if(!_hash[i]&&rec(index,i)) {
			_hash[i]=true;
			result[index]=i;
			if(dfs(index+1)) 
				return true;
			_hash[i]=false;
		}
	}
	return false;
}

int main()
{
	prim();
	while(~scanf("%d%d%d",&n,&m,&d),n) {
		num=m-n+1;
		memset(result,0,sizeof(result));
		memset(_hash,0,sizeof(_hash));
		if(dfs(0)) {
			printf("%d",result[0]);
			for(int i=1;i<num;++i)
				printf(",%d",result[i]);
			puts("");
		}else
			puts("No anti-prime sequence exists.");
	}
	return 0;
}



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章