算法——回溯法
2012-07-10 09:30
155 查看
回溯法
回溯法有“通用的解题法”之称。用它可以系统地搜索一个问题的所有解或任一解。回溯法是一种即带有系统性又带有跳跃性的搜索算法。它在问题的解空间树中,按深度优先策略,从根节点出发搜索解空间树。算法搜索至解空间树的任一结点时,先判断该节点是否包含问题的解。如果不包含,则跳过对以该节点为根的子树的搜索,逐层向其它祖先节点回溯。否则,进入该子树,继续按照深度优先策略搜索。回溯法求问题的所有解时,要回溯到根,且根节点的所有子树都已被搜索遍才结束。回溯法求问题的一个解时,只要搜索到问题的一个解就可结束。这种以深度优先方式系统搜索问题的算法称为回溯法,它是用于解组合数大的问题。问题的解空间
用回溯法解问题时,应明确定义问题的解空间。问题的解空间至少包含问题的一个(最优)解。例如对于有n种可选择物品的0-1背包问题,其解空间由长度为n的0-1向量组成。该解空间包含对变量的所有可能的0-1赋值。例如n=3时,其解空间是{(0,0,0),(0,0,1),(0,1,0),(0,1,1),(1,0,0),(1,0,1),(1,1,0),(1,1,1)}
定义了问题的解空间后,还应该将解空间很好地组织起来,使得能用回溯法方便地搜索整个解空间。通常将解空间组织成树或者图的形式。
例如,对于n=3时的0-1背包问题,可用一颗完全的二叉树表示其解空间,如下图。
n后问题
//八皇后问题 // Queen.cpp : 定义控制台应用程序的入口点。 // #include "stdafx.h" #include "stdio.h" class Queen{ //类Queen记录解空间中的节点信息 friend int nQueen(int); private: bool Place(int k); //剪枝函数 void Backtrack(int t); //递归函数 int n; //皇后个数 int *x; //当前解 long sum; //当前可行的方案数 }; int abs(int ab)//求绝对值 { return ab>0?ab:-ab; } bool Queen::Place(int k) //剪枝函数 { for(int j=1;j<k;j++) { //剪枝条件:如果在同一行,同一列或者同斜线上 if((abs(k-j)==abs(x[j]-x[k]))||(x[j]==x[k])) return false; } return true; } void Queen::Backtrack(int t) //递归回溯核心 { if(t>n) sum++; //如果遍历到叶子,说明求出了一个解 else for(int i=1;i<=n;i++) { x[t]=i; if(Place(t)) Backtrack(t+1); //函数Place为剪枝函数 } } int nQueen(int n)//初始化数据 { Queen X; X.n=n; X.sum=0; int *p=new int[n+1]; for(int i=0;i<=n;i++) { p[i]=0; } X.x=p; X.Backtrack(1); delete []p; return X.sum; } int _tmain(int argc, _TCHAR* argv[]) { printf("%d",nQueen(8));//传入参数8,即八皇后问题 return 0; }
测试结果:带入参数8,得到92种解,这个符合答案。
参考资料
维基百科:八皇后问题http://zh.wikipedia.org/wiki/%E5%85%AB%E7%9A%87%E5%90%8E%E9%97%AE%E9%A2%98计算机算法设计与分析/王晓东编著。-3版。-北京:电子工业出版社,2007.5相关文章推荐
- 算法分析与设计实验三 回溯法 24点问题 n皇后问题
- 五大常用算法之四:回溯法
- 常用算法:分治算法、动态规划算法、贪心算法、回溯法、分支限界法
- 0x08算法设计与分析复习(二):算法设计策略-回溯法2
- [回溯法]从蛮力算法起步,谈八皇后问题的求解:
- 算法java实现--回溯法--图的m着色问题
- 【数据结构与算法】backtracking 回溯法
- 八皇后(N皇后)问题算法程序(回溯法)
- 算法java实现--回溯法--装载问题
- 回溯法算法步骤&n皇后问题的详细程序(C++)
- 经典算法(1)——8皇后问题求解(回溯法)
- 五大常用算法之四:回溯法
- 算法系列—回溯法
- 【DayDayUp】【算法_图_哈密顿回路_之一_回溯法】(待补完)
- 0x08算法设计与分析复习(二):算法设计策略-回溯法3
- 算法java实现--回溯法--最大团问题
- 算法-回溯法解决最佳调度问题
- 【算法学习笔记】61.回溯法 DFS SJTU OJ 1106 sudoku
- C语言算法—比赛试题(x星球的人员安排)【有错误代码,望大神们指点】(类似建立树的回溯法)
- 编程之美1.15节:构造数独算法-回溯法和置换法