您的位置:首页 > 其它

HDOJ1016 素数环(DFS)

2012-10-09 10:58 218 查看
题目:

1016Prime Ring Problem
/*
素数环(顺时针逆时针)---dfs
使用栈
1-n(n最大是20,相邻最大和39,素数范围2-39之间)
2-39间的素数:
2,3,5,7,11,13,17,19,23,29,31,37
从1开始,逐个尝试,如果是素数,入栈,否则尝试下一个,直到全部尝试完;
如果n个数全部入栈了,输出一组解(n最大为20,输出栈可以使用递归),
第一个数始终是1,第二个数需要尝试n+1的时候,就表示结束了(next = -1)。
*/
#include <cstdio>
#include <iostream>
#include <stack>
using namespace std;

#define N    22
//全局变量
int prime[40];
int arr
;
stack<int> s;

//函数
void InitPrime();
void InitArr(int n);
void dfs(int n);
int GetNext(int b,int n);
void Output(int n);
//main
void main()
{
int n;
InitPrime();
while (scanf("%d",&n)!=EOF)
{
InitArr(n);
dfs(n);
}
}

void InitPrime()
{
for (int i=0;i<40;i++)
{
switch(i)//本题数量不多,就直接这样写啦,如果数量多可以用【筛选法】或者【试除法】
{
case 2:        case 3:        case 5:
case 7:        case 11:    case 13:
case 17:    case 19:    case 23:
case 29:    case 31:    case 37:
prime[i] = 1;
break;
default:
prime[i] = 0;
}
}
}

void InitArr(int n)
{
for (int i=1; i<=n ; i++)
{
arr[i] = 0;
}
}
void dfs(int n)
{
int flag,next,b,idx;
s.push(1);
arr[1] = 1;
flag = 1;
idx = 1;//从idx开始寻找匹配数字
while (flag)
{
b = s.top();
next = GetNext(idx,n);
if (next == -1)//尝试结束,回溯
{
if (b == 1 && next == -1)//over
{
flag = 0;
}
idx = s.top();
s.pop();
arr[idx] = 0;
continue;
}
if (prime[next+b] == 1)//匹配成功,next入栈,idx化为2
{
arr[next] = 1;
s.push(next);
idx = 1;
//全部入栈则输出
if (s.size() == n && prime[1+s.top()] == 1)//既要顺时针为素数环又要逆时针为素数环
{
Output(n);
cout<<endl;
idx = s.top();
s.pop();
arr[idx] = 0;
}
continue;
}
//匹配失败,idx化为next
idx = next;
}

}
int GetNext(int b,int n)
{
for (int i=b+1;i<=n;i++)
{
if (arr[i]!=1)
return i;
}
return -1;//全部尝试完返回-1
}
void Output(int n)
{
int cur;
if (n!=0)
{
cur = s.top();
s.pop();
Output(n-1);
cout<<cur<<' ';
s.push(cur);//还要加回去
}
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: