四、传播

1、草药迷阵问题

\qquad 有一个10*10的百草药柜,每一个抽屉里都有5种不同属性的草药,依次打开抽屉来长出草药迷阵,要求寻找一种神奇的药方,满足:

  • 横行:每一种被选取的草药都要和相邻的抽屉里选的草药相互符合相生相克的关系
  • (1,1) 不能从抽屉里选取金属性的草药
  • 纵列:最少一种,最多两种金属性和土属性的草药

2、时序回溯搜索

\qquad 首先列举可能的选择来做决策:
\qquad \qquad - 选择一个决策
\qquad \qquad - 在所有现有的可能性里面选择一个,且保证这个选择跟目前为止已做的决策是“兼容的”
\qquad \qquad - 如果当前的选择与某些约束冲突了,考虑另一个可行的选择
\qquad 如果所有的决策都互相兼容,那么我们就找到一个解
\qquad 如果在任意一个步骤,没有任何可行的选择作为决策,则修改上一个决策
\qquad 时序回溯搜索其实是一个搜索树的搜索过程,其示意如下图所示:
在这里插入图片描述
\qquad 为了更好地程序化时序回溯搜索算法,首先做出下述定义,令 f i x ( D ) fix(D) fix(D)表示一个变量的集合,其中的所有变量 X X X都已经被赋予一个数值,称 f i x ( D ) fix(D) fix(D)中的变量为已经被固定的变量;令 s a t i s f i e d ( c ) satisfied(c) satisfied(c)表示一个函数,用于检查某一条约束 c c c的变量是否都已经被固定了。令 c h e c k ( C , D ) check(C,D) check(C,D)表示一个函数,用于检查约束集合 C C C中的所有约束的值域。

 check(C,D):
 	foreach c in C:
 		if(vars(c) in fixed(D)):
 			if not satisfied(c) return false domain #约束c中不是所有变量均已被固定
 	return D 									#约束c中所有变量均已被固定

\qquad 基本回溯搜索算法的流程如下所示:

back_search(C,D):
	if(vars(C) in fixed(D)) return check(C,D)
	X = choose(vars(C)-fixed(D))#选择下一个尝试固定的变量
	foreach d in D(X):
		D1 = check(C and {X=d}, D)
		if(D1=D):
			D2 = back_search(C and {x=d}, D)
			if(D2 is not a false domain) return D2
	return false domain

\qquad 在搜索里,变量的顺序(choose())的影响十分大,不同的选择直接影响到搜索树的大小的搜索效率;
\qquad 函数 c h o o s e ( ) choose() choose()允许采用不同的方法选择下一个变量,最简单的方法是根据他们的输入顺序依次进行选择;也可以基于其他规则进行选取,如根据变量值域的大小,选择值域最大或者最小的变量。
\qquad 在对某个变量的值域进行搜索时,i.e., foreach d in D(X),搜索的顺序会影响到搜索的效率,好的选择可以使得可行解更早地被找到,从而加速剪枝和缩短求解时间。

3、传播+搜索

\qquad 约束传播是一个有效且高效的推理方式,可以从变量的值域中移除那些确保不会出现在解中的数值,从而可以得到更小的值域和更小的搜索树。
\qquad 应用约束+传播的思路为:在每一个搜索节点上,在枚举搜索下一个变量之前,进行约束传播。
\qquad 将约束传播技术融入到搜索过程,得到的强化版本的搜索-传播算法如下所示:

prop_search(F0,Fn,D):
	D = isolv(F0,Fn,D) #通过约束传播更新值域
	if(D is a false domain) or (all X: |D(X)| =1):
		return D
	X = choose(vars(C))
	foreach d in D(X):
		D1 = back_search(F0 and Fn, {prop(X=d)}, D)
		if(D1 is not a false domain) return D1
	return false domain

\qquad 使用二叉分枝的方法如下所示:
在这里插入图片描述
\qquad 上述二叉分枝中, c h o o s e ( D ) choose(D) choose(D)函数用于将父结点划分成两个子结点,其中的划分方法可以有如下几种,首先选择一个变量 X X X,其值域中的值的个数 ∣ D ( X ) ∣ > 1 |D(X)|>1 D(X)>1,在其值域中选择一个值 d ∈ D ( X ) d \in D(X) dD(X)。第一种方法是:在一个分枝中令 X = d X=d X=d,在另一个分枝结点中令 X ≠ d X \neq d X=d。另外一种分枝方法是:在一个分枝中令 X ≤ d X \leq d Xd,在另一个分枝中令 X ≥ d + 1 X \geq d+1 Xd+1。上述分枝方法在约束传播中叫做值域分割。

THE END

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Dragon Fly

多谢老板赏钱[抱拳抱拳抱拳]

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值