HDU——1016 Prime Ring Problem (DFS的簡單應用)
阿新 • • 發佈:2018-12-18
A ring is compose of n circles as shown in diagram. Put natural number 1, 2, …, n into each circle separately, and the sum of numbers in two adjacent circles should be a prime.
Note: the number of first circle should always be 1.
The output format is shown as sample below. Each row represents a series of circle numbers in the ring beginning from 1 clockwisely and anticlockwisely. The order of numbers must satisfy the above requirements. Print solutions in lexicographical order.
You are to write a program that completes above process.
Print a blank line after each case.
大致意思是:
有一個n個點組成的環,在每一點中在 1~n中選取一個數字 使得該點與相鄰的點 的和是一個素數(第一個點必須是1)
舉例 n=6時
其中一種可能為:1 4 3 2 5 6
滿足第一個點是1,且 1+4=5為素數,4+3=7為數數,3+2=5為素數(依次類推) 當最後一個數時與第一個數相加
AC程式碼如下:
#include <iostream>
#include <cmath>
#include <cstring>
using namespace std;
const int maxn=25;
int a[maxn]; //用來儲存數字環
int n;
bool isok[maxn]; //用來標記某個數字是不是已經選過了
bool isprime(int x) //用來判斷該數是不是素數
{
if(x==1)
return false;
else
for(int i=2;i<=sqrt(x);i++)
if(!(x%i))
return false;
return true;
}
void dfs(int k)
{
if(k==n && isprime(a[k-1]+a[0]) ) //遞迴的結束條件 如果遞迴到最後一個點,且最後一個點也滿足情況就輸出
{
for(int i=0;i<n;i++)
if(i)
cout<<' '<<a[i];
else cout<<a[i];
cout<<endl;
}
else
{
for(int i=2;i<=n;i++) //第一個點的數字已經確定,所以就從2~n開始找
if(!isok[i]) //如果這個數前面沒有標記過 那麼就採用這個數
{
a[k]=i;
isok[i]=true;
if(isprime(a[k]+a[k-1])) //放入該點後是素數
dfs(k+1); //繼續下一個點
isok[i]=false; //最後將標記取消!(重要!!)
}
}
}
int main()
{
memset(isok,0,sizeof(isok));
a[0]=1;
int kase=1;
while(cin>>n)
{
cout<<"Case "<<kase++<<':'<<endl;
dfs(1);
cout<<endl;
}
return 0;
}