第 5 章 艰苦卓绝

相关主题
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
• 在一个无向图G=<V, E>中,寻求从顶点s出发,经 过G中每一个顶点一次,最后回到顶点s的回路, 这个问题称为Hamilton回路问题。
1.问题的理解与描述
• Hamilton回路问题可形式化地描述为: • 输入:具有n个顶点的无向图G=<V, E>,起 始顶点s。 • 输出:如果G具有Hamilton回路,输出所有 向量x=<x1, x2, …, xn>,其中,x1, x2, …, xn是1, 2, …, n的一个排列,且x1, x2, …, xn, x1是G中 的一条回路。否则,输出无解信息。
5.2.1 算法框架
• 把上述分析得到的刻画组合问题各自特性 的动态属性统一地表示为: • IS-COMPLETE——判断问题的解是否合法。 • PRINT-SOLUTION—— 打印一个合法解。 • MAKE-ITERMS—— 生成当前节点的取值集合。 • IS-PARTIAL—— 判断部分解。 • 引导与探索过程统一为:
5.1.4 子集和问题
• 1.问题的理解与描述 • 子集和问题是在一个整数集合A={a1, a2, …, an} 中,寻求一个子集合A '⊆A,使得A '中元素之 和等于给定的整数C。例如整数集合A={1, 2, 3, 4},整数值C=6,则A的子集{1, 2, 3},{2, 4}都是 合法解。问题的形式化描述如下。 • 输入:整数集合A={a1, a2, …, an},整数值C。 • 输出:向量x=<x1, x2, …, xn>,其中xi∈{0, 1},若 ai∈A', xi=1,否则xi=1,i=1, 2, …, n。使得 =C。
3.算法的运行时间
• 在最坏情形下将产生完全n叉树中Θ(nn)个节 点,对每一个产生的节点(x[k]的一个取值) 第8~10行判断其是否能与x[1...k-1]一起, 使得x[1...k] 构成一个部分解需要用Θ(n)时间。 所以,最坏情形下总的运行时间为Θ(nn+1)。
5.1.3 Hamilton回路问题
2.算法的伪代码描述
• • • • • • • • • • • • • • • • • • SUBSET-SUM (A, C) 1 flag←false 2 为解向量x分配存储空间 3 PICK (1) 4 if flag=false 5 then error "no solution" PICK (k) 1 if k>n 2 then if 判断是否为完整解 3 then flag← ture 4 for i←1 to n 打印合法解 5 do if xi=1 6 then print A[i] 7 return 8 for i←0 to 1 逐一尝试可能的取值 9 do xk←i 10 if 判断是否为部分解 11 then PICK (k+1)
第 5 章 艰苦卓绝
回溯算法
5.1 组合问题与回溯算法
• 很多现实问题中,合法的解可能要通过在 一个大量但有限多种可能性中做穷尽搜索 才能获得,这样的问题通常称之为组合问 题。 • 一种通用的称为回溯的搜索技巧用来在穷 尽搜索过程中,能避免搜索所有的可能情 形。它普遍地适用于解决需要检测有限但 却是大量的可能解的组合问题。
3.算法的运行时间
• 在最坏情形下将产生完全二叉树中Θ(2n)个 节点,对每一个产生的节点(xk的一个取值) 第10行判断其是否能与x1...xk-1一起,使得 x1...xk 构成一个部分解需要用Θ(n)时间。所 以,最坏情形下总的运行时间为Θ(n2n)。
5.2 解决组合问题的回溯算法框架
• 仔细考察上述4个问题的回溯算法,很容易发现它们非 常相似。首先,引导过程THREE-COLOR, N-QUEENS , HAM-CIRCUIT和SUBSET-SUM除了过程名和其中调用的探 索算法过程名不同外,完全一致。其次,探索过程 GRAPH-COLOR, PLACE , EXTEND和PICK除了算法的过 程名不同,还有下列几点不同之处: • (1)判断一个合法解的条件 • (2)输出合法解的方法 • (3)解向量的每个分量的可能取值 • (4)判断一个部分合法解的条件 • 除了这些不同点,探索算法从结构上而言,也是一样的。 由此,启发我们把组合问题从算法中分离出来,形式化, 然后用一个统一的回溯算法框架来解决这些组合问题。
(a)
(b)
1.问题的理解与描述
• 我们将n-皇后问题形式化为: • 输入:棋盘规模n。 • 输出:如果此n×n棋盘存在合法格局,则输 出所有由向量x=<x1, x2, …, xn>,其中,x1, x2, …, xn是1, 2, …,n的一个排列,且∀(1 i ≠ j n)有xi – xj ≠ i – j且xi – xj ≠ j–i决定的格局: 棋盘上的第i行第xi格放置一个皇后,i=1, 2, …,n。否则,输出无解信息。
• • • • • • • • • • • • • • • • • • •
BACKTRACK(P) 1 flag←false 2 为解向量x分配存储空间 3 EXPLORE(P,1) 4 if flag=false 5 then error "no solution" EXPLORE(P, k) 1 if IS-COMPLETE(x) 2 then flag← ture 3 PRINT-SOLUTION(x) 4 return 5 if k>n 6 then return 7 iterms←MAKE-ITERMS(k) 8 m←length[iterms] 9 for i←1 to m 对当前第k个分量逐一检测各种可能的取值 10 do x[k]← iterms[i] 11 if IS-PARTIAL(x, k) 得到部分解 12 then EXPLORE(P, k+1)
2.算法的伪代码描述
• • • • • • • • • • • • • • • • • • • N-QUEENS (n) 1 flag←false 2 为解向量x分配存储空间 3 PLACE(1) 从根起对以下第1层节点进行搜索 4 if flag=false 5 then error "no solution" PLACE (k) 1 if k>n 判断是否为完整解 2 then flag← ture 3 for i←1 to n 4 do 输出棋盘中第i行格局 5 return 6 for colum←1 to n 对当前第k行逐一检测各种可能的位置 7 do x[k] ← colum 8 for i←1 to k-1 9 do if x[i] = x[k] or |x[i] – x[k]|=| i – k| 10 then 检测第k行的下一个置放位置 11 PLACE (k+1) 进入下一层搜索
2.算法的伪代码描述
• • • • • • • • • • • • • • • • • • • • • • HAM-CIRCUIT (G) 1 flag←false 2 为解向量x分配存储空间 3 EXTEND (1) 从根起对以下第1层节点进行搜索 4 if flag=false 5 then error "no solution" EXTEND (k) 1 if k>n 2 then if x[n]与x[1]在G中相邻判断是否为完整解 3 then flag← ture 4 print x 5 print x[1] 6 return 7 if k=1 8 then x[k] ←s 9 EXTEND (x, k+1) 10 else for G中每一个与x[k-1]相邻的顶点u 11 do x[k] ← u 12 for i←1 to k-1 13 do if x[i] = x[k] 14 then 检测下一个与x[k-1]相邻的顶点 15 EXTEND (k+1) 进入下一层搜索
3.算法的运行时间
• 最坏情形下将产生完全n-1叉树(G是一个 完全图时)中的Θ(nn)个节点,对每一个产 生的节点(x[k]的一个取值)第10~14行判 断其是否能与x[1...k-1]一起,使得x[1...k] 构 成一个部分解需要用Θ(n)时间。所以,最坏 情形下总的运行时间为Θ(nn+1)。
2.算法的伪代码描述
• • • • • • • • • • • • • • • • • THREE-COLOR(G) 1 flag←false 2 为解向量x分配存储空间 3 GRAPHCOLOR(1) 从根起对以下第1层节点进行搜索 4 if flag=false 5 then print "no solution." GRAPH-COLOR(k) 1 if k>n判断是否为完整解 2 then flag←true 3 print x 4 return 5 for color←1 to 3 对当前第k个顶点逐一检测3种可能的着色 6 do x[k] ←color 7 for i←1 to k-1 8 do if i, k 在G中相邻且x[i]=x[k] 9 then 检测x[k]的下一种着色 10 GRAPH-COLOR(k+1) 进入下一层搜索
a b d (a) b=2 b=3 e c a=1
树根
b=1 c=1 d=1
c=2 d=2
c=3 d=3 e=1 e=2 e=3
c=1
c=2 d=1
c=3 d=2 d=3
e=1 e=2 e=3
e=1 e=2 e=3e=1 e=2 e=3 (b)
• (a)表示图G,我们要对其顶点用颜色{1, 2, 3}来着色。(b)部分展示了合 法着色方案形成过程中搜索树的路径。首先,在产生出第三个结点后, 发现着色方案<1, 1>不是合法部分解,所以该节点在图中用×标识为死 结点。接着b涂成颜色2,这样着色方案<1, 2>看起来是一个部分解。 于是产生一个对应于顶点b的新的孩子结点,其初始着色为1。重复上 述过程,最终将得到一个合法的着色方案<1, 2, 2, 1, 3>。
x1=2
x2=4
X
x3=1
x4=3
对于n=4的情形,x1置为1且x2置为1。这将导致一个死节点,因为这 两个皇后置于同一列中。若x2置为2也将发生同样的结果,因为这两 个皇后置于同一斜线上。将x2置为3将导致一个部分解向量<1, 3>且探 索对x3寻求一个值。如图中所示,无论x3假设为何值,都不会得到 x1=1, x2=3 及x3>0的部分解。所以搜索回溯到第二层并对x2赋予一个新 的值,即4。如图所示,这导致了部分解向量<1, 4, 2>。此向量还是不 能被扩展,在产生出一些新的节点后,搜索回到第一层。现在,x1增 加为2,以同样的方式,找到部分解向量<2, 4, 1>。如此,此向量被扩 展为合法向量<2, 4, 1, 3>,这就对应一个合法解。
3-着色问题
• 1.问题的理解与描述 • 假定图G的顶点集合为V={1, 2, …, n},则3-着 色问题形式化为: • 输入:图G=<V, E>。 • 输出:若G存在各顶点的合法着色方案,输 出所有解向量c=<c1, c2, …, cn>,其中1≤ci≤3 为G的第i个顶点的着色,且对∀(i, j)∈E,ci ≠ cj。否则输出无解信息。
3.算法的运行时间
• 注意在最坏情形下将产生Θ(3n)个节点,对 每一个产生的节点(x[k]的一个取值)第 7~9行判断其是否能与x[1...k-1]一起,使得 x[1...k] 构成一个部分解需要用Θ(n)时间。所 以,最坏情形下总的运行时间为Θ(n3n)。
5.1.2 n-皇后问题
• 如何在一个8×8的棋盘上放置8个皇后使得 任意两个皇后之间不能相互攻击?
1
2 5
Fra Baidu bibliotek
3
4 (a) 1
2 3 1 2 4 2
3
4 4 3 1 2 4 2
1
5 4 1 3 5
1 1
2
1
5 4
3 5 1 3 5 2 4 (b) 2 4
1 3 5
1 3 5 1 3 5
• 为寻求(a)中起始顶点为顶点1的Hamilton回路,其搜索树如图 (b)所示。 树根对应起始顶点,根下第1层节点对应与起始顶点相邻的顶点。第2 层节点对应与第1层节点对应的那些顶点相邻的顶点,以此类推。回 溯法从根节点开始,按深度优先原则在此树中搜索:对解向量中第k-1 个分量所代表的顶点的每个相邻顶点检测是否能扩展成第k个分量。 若检测到,则递归进入下一层。若所有与x[k-1]相邻的顶点都不能成为 合法的x[k],则回溯到上一层。
0 0 0 0 1 0 1 0 10 1 0 1 1 1 0 0 10 0 1 10
1 1 0 1 0 1 1
• 按深度优先原则在搜索树中搜索:对当前 节点,分别用0,1检测x1...xk是否构成一个 合法部分解。若是,则递归进入下一层。 若0和1都不能使xk与x1...xk-1一起构成合法部 分解,则回溯到上一层。
相关文档
最新文档