本文参考了其他博文,参考出附上了原文链接。侵权联系我删除!
1.算法介绍
回溯算法是一个既带有系统性,又带有跳跃性的搜索算法:
系统性:它在包含问题的所有解空间树中,按照深度优先策略,从根节点出发搜索解空间树
跳跃性:算法搜索至解空间树的任一节点时,判断该节点为根的子树是否包含问题的解,如果肯定不包含,则跳过搜索以该节点为根的子树的搜索,逐层向其祖先节点回溯。否则进入该子树,继续按深度优先策略搜索
2.解空间树
解空间树有三种节点,根节点、中间节点、叶节点,当搜索到达叶节点,表明可能找到一个解。回溯算法常见的的解空间树包括两种:子集树和排列树。常见的用子集树解决的问题,如0-1背包问题;用排列树解决的问题,如TSP(旅行商)问题。
Tips:提高回溯法效率的两种方法
(1)用约束函数减去不满足约束的子树
(2)用限界函数减去不能得到最优解的子树
3.子集树
例1【0-1背包】
物品数量n=3,重量w=(10,8,5),价值v=(5,4,1),背包容量c=16,求解背包所能装下的最大价值
(1)定义解空间:X={(0,0,0),(0,0,1),(0,1,0),...,(1,1,0),(1,1,1)},0表示不装入背包,1表示装入背包
(2)构造解空间树:
(3)从A出发按DFS搜索
package com.zqi.backtracking;
/**
* 递归就是自己调用自己,一层执行完,返回给上一层的调用者,一层层返回回去
*/
public class ZeroOneBag {
public static final int N = 3;
public static final int C = 16;
public static int[] w = {10,8,5}; //每个物品的重量
public static int[] v=