回溯算法求素数环

原文地址:http://www.cnblogs.com/xwz0528/p/4638242.html

一. 问题描述

把从1到n(n>=2)这n个数摆成一个环,要求相邻的两个数的和是一个素数,找出所有满足条件的环。

二. 问题分析

1> 解向量:<x1, x2, ··· , xn>

2> 解空间树:排列树,(n-1)!个叶子结点

3> 剪枝函数:isPrime( x[t-1]+x[t] ),t=2,3,···,n  约束函数

三. 算法实现

 1 #include<iostream>
 2 #include<math.h>
 3 using namespace std;
 4
 5 int n;//素数环中的数字个数
 6 int sum=0;//可行方案数
 7 int arr[100];//存放素数环
 8
 9 bool isPrime(int x)
10 {
11     int i;
12     int k=(int)sqrt(x);
13     for(i=2;i<=k;i++)
14     {
15         if(x%i==0)
16         {
17             return false;
18         }
19     }
20     return true;
21 }
22
23 //回溯法
24 void backtrack(int t)
25 {
26     int i;
27     if(t>n)//搜索到叶子结点
28     {
29         if(isPrime(arr[n]+arr[1]))
30         {
31             sum++;
32             for(i=1;i<=n;i++)
33             {
34                 cout<<arr[i]<<" ";
35             }
36             cout<<endl;
37         }
38     }
39     else
40     {
41         for(i=t;i<=n;i++)
42         {
43             swap(arr[t],arr[i]);
44             if(isPrime(arr[t-1]+arr[t]))
45             {
46                 backtrack(t+1);
47             }
48             swap(arr[t],arr[i]);
49         }
50     }
51 }
52
53 void main()
54 {
55     int i;
56     cout<<"请输入素数环中数字的个数:";
57     while(cin>>n)
58     {
59         sum=0;
60         for(i=1;i<=n;i++)
61         {
62             arr[i]=i;
63         }
64         backtrack(1);
65         cout<<"可行方案数为:"<<sum<<endl;
66         cout<<"----------------"<<endl;
67         cout<<"请输入素数环中数字的个数:";
68     }
69 }
时间: 2024-11-09 00:56:44

回溯算法求素数环的相关文章

回溯算法之素数环

using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace SeqListSort { /// <summary> /// <ather> /// lihonglin /// </ather> /// <content> /// 把从1到20这20个数摆成一个环,要求相邻的两个数的和是一个素数. ///分析:用回溯算法,考察所有

算法练习--素数环

输入一个数字n,输出[1,N]内的全部组合,满足a[i]+a[i+1]为素数.当中i∈[0,i-1] 比如输入:6 输出:1,4,3,2,5,6 实现: var MAX = 10; ////setup prime array var primeArr = new Array(); var Ann = function a(arr){ if(arr.length <= 1){return arr;} var rr = new Array(); for(var i = 0; i<arr.lengt

回溯算法求关于排列有关问题

八皇后问题就是一个典型的全排列问题了,这个在有一篇博客已经写过了,但是今天想在这里对于排列问题来一个总结. 排列问题主要涉及到以下几个方面: 1.不带重复数的全排列 2.带重复数的全排列 3.有限个数的全排列(例如从n个数里面选择m个数,m<n) 现在就以上几个方面把代码给大家,能理解则理解,不能理解就背下来,这种解法效率还是挺高的. 代码前提:所有的数据我都默认从0到n-1,如果在实际运用中,有可能需要进行变化. 1.不带重复数的全排列 #include<iostream> using

搜索与回溯 - 素数环

[题目描述] 从1到20,这20个数摆成一个环,要求相邻的两个数的和是一个素数.求所有可能. [算法分析&&参考代码] 1 #include <iostream> 2 #include <cmath> 3 using namespace std; 4 int a[21],ans=0; //a数组表示第几个位置的数是啥. 5 bool b[21]={0}; //b数组表示标记,这个数用过没有? 6 bool pd(int,int); 7 void dfs(int);

ACM:回溯法,八皇后问题,素数环

(一)八皇后问题 (1)回溯法 #include <iostream> #include <string> #define MAXN 100 using namespace std; int tot = 0, n = 8; int C[MAXN]; void search(int cur) { if(cur == n) ++tot; //递归边界,只要走到了这里,所有皇后必然不冲突 else for(int i = 0; i < n; ++i) { int ok = 1; C

素数环

问题描述: 将从1到n这n个整数围成一个圆环,若其中任意2个相邻的数字相加,结果均为素数,那么这个环就成为素数环. n=20时,下面的序列就是一个素数环: 1 2 3 4 7 6 5 8 9 10 13 16 15 14 17 20 11 12 19 18 php版本回溯算法: 1 <?php 2 //素数环问题 3 include "show.php"; 4 5 define("LEN", 20); 6 7 class Primes 8 { 9 privat

DFS ( 深度优先/回溯算法 ) 一

    深度优先搜索算法(英语:Depth-First-Search,简称DFS)是一种用于遍历或搜索树或图的算法. 沿着树的深度遍历树的节点,尽可能深的搜索树的分支.当节点v的所在边都己被探寻过或者在搜寻时结点不满足条件,搜索将回溯到发现节点v的那条边的起始节点.整个进程反复进行直到所有节点都被访问为止.属于盲目搜索,最糟糕的情况算法时间复杂度为O(!n).(Wiki) DFS在搜索过程常常伴随许多优化策略,增加剪枝函数,或者和动态规划结合. 让我们用一道看似简单的例子理解DFS. = = /

ACM/ICPC 之 最长公共子序列计数及其回溯算法(51Nod-1006(最长公共子序列))

这道题被51Nod定为基础题(这要求有点高啊),我感觉应该可以算作一级或者二级题目,主要原因不是动态规划的状态转移方程的问题,而是需要理解最后的回溯算法. 题目大意:找到两个字符串中最长的子序列,子序列的要求满足其中字符的顺序和字母在两个序列中都必须相同,任意输出一个符合题意的子序列 首先是最基本的最长公共子序列的状态转移问题: 这里的maxLen[i][j]数组的意思就是保存s1的前 i 个字符和s2的前 j 个字符匹配的状态. 举个例子:maxLen[3][6]即表明在s1的前3个字符和s2

C程序设计的抽象思维-回溯算法-迷宫问题

[迷宫问题] 两种方法:1. 堆栈回溯,2.递归回溯. [算法1---堆栈回溯] 计算机解迷宫时,通常用的是"试探和回溯"的方法,即从入口出发,顺某一方向向前探索,若能走通,则继续往前走:否则沿原路退回,换一个方向再继续探索,直至所有可能的通路都探索到为止,如果所有可能的通路都试探过,还是不能走到终点,那就说明该迷宫不存在从起点到终点的通道. 1.从入口进入迷宫之后,不管在迷宫的哪一个位置上,都是先往东走,如果走得通就继续往东走,如果在某个位置上往东走不通的话,就依次试探往南.往西和往