标签:
6 8
Case 1: 1 4 3 2 5 6 1 6 5 2 3 4 Case 2: 1 2 3 8 5 6 7 4 1 2 5 8 3 4 7 6 1 4 7 6 5 8 3 2 1 6 7 4 3 8 5 2
输入n 原数列:1 2 3 ... n
解空间树思想求解,递归、回溯。相邻的每一个数都要求是素数,把第一数设定为 1 ,当然了是几都可以的,1有 n-1中选择,先从2开始往后选,符合条件放入a数组,由符合条件的这个数重复以上操作,直到最后一个确定出来则打印。
DFS深层理解:
原来对DFS的理解仅仅局限于图,现在发现这只是最基础的。DFS更多的表示的是一种状态,然后利用某中很简单的思维进行一次次的尝试,每次尝试成功了,就 深入一层递归进行下一次尝试,直到之后的尝试表明已经失败了不会成功,则回溯到这里。取消这次的尝试,去尝试其他的操作。简单地说,就是暴搜。只不过利用 了递归来实现尝试失败时的回溯,从而进行新的尝试。
代码:
#include <stdio.h> #include <math.h> bool use[21]; int a[21]; int n; bool isprime(int m) { int i; for(i = 2; i <= sqrt(m); i++) { if(m%i == 0) { return false; } } return true; } void init(int n) { int i; for(i=0; i < n; i++) { use[i] = false; } a[0] = 1;//让第一个数是1,因为是一个圆,是其他任何数都可以 } void dfs(int num)//搜索当前第num位置应该放的数字 { int i; if(num == n && isprime( 1 + a[n-1]))//最后一个位置的比较 { for(i=0;i<n;i++)//打印出来 { printf( i == n-1 ? "%d\n" : "%d ",a[i]); } } else { for( i = 2; i <= n; i++)//枚举每一个数 { if( isprime( i+a[num-1]) && !use[i] )//如果这个数符合和当前数成素数的条件并且没有使用过,就把它作为当前的下一个的相邻数 { a[num] = i;//a[]存的是满足条件的数 use[i] = true; dfs(num+1);//继续搜索下一个位置的数 use[i] = false;//回收重新使用 } } } } int main() { int t = 0; while(~scanf("%d",&n)) { printf("Case %d:\n",++t); init(n); dfs(1); puts(""); } return 0; }
HDOJ1016 Prime Ring Problem(DFS深层理解)
标签:
原文地址:http://www.cnblogs.com/ldy-miss/p/5760386.html