基于DPLL的N皇后问题解

本文探讨了如何将N皇后问题转化为SAT问题,并利用DPLL算法求解。逻辑命题转化器将约束条件转换为CNF形式,DPLL求解器用于判断满足性并收集解的过程。单一解生成器与取反循环辅助生成所有解组合,揭示了皇后布局的解集和计数方法。
摘要由CSDN通过智能技术生成

[ 问题 ]

在 n×n 格的棋盘上,放置 n 个皇后于 n 个格子中
使得不存在任意两个皇后位于同一行、同一列、同一斜线上
输出对应存在的摆放组数 f(n) 和摆放方式

[ SAT问题 ]

把约束条件写成逻辑表达式,向逻辑可满足性问题SAT转化
再基于DPLL或CDCL求解

[ 输出解集 ]

DPLL和CDCL为可满足性算法,不能直接产生解集和解的数量
但可以以此为基础,依次将当前解的否定纳入逻辑命题,从而计算下一组解
直至不可满足,返回storage中所有解

[ 框架思路 ]

整体主要分为四个部分:
    |—— 逻辑命题转化器
    |—— DPLL求解器(可满足性 + 部分命题赋值确定)
    |—— 单一解生成器
    |__ 单一解取反循环
- 逻辑命题转化器
    对于SAT问题,可以写出相应的逻辑命题合取范式CNF
    将CNF用谓词和量词逻辑重写,程序便可以扫描遍历
    扫描结果存于列表q,便是向求解器输入的展开的合取范式
    根据波兰表达式规则,可单次扫描完成
- DPLL求解器
    DPLL本身只用于可满足性判断
    但通过在赋值过程中记录赋值,并在结果为 True 的回溯结束时存储
    就可以收集该单一解所要求的赋值
    [N] 其中一些赋值引向 False,必须在一轮结束时舍弃,具体细节在代码部分讨论

- 单一解生成器
    根据一次DPLL运行生成的已赋值变量,对求解过程删除的所有子句重新分析
    去除所有已赋值变量,剩余任意赋值,便为一组解
    每轮的解存进storage,并将临时容器清空进行下一轮
- 单一解取反循环
    将一次运行获得的解集内全部文字取反,作为新子句纳入CNF
    以新CNF重新运行DPLL
    重复直至CNF不可满足,storage里便是该SAT问题的所有解

N皇后逻辑命题转化

P ( i , j ) P(i,j) P(i,j) 表示 ( i , j ) (i,j) (i,j) 处存在皇后, ¬ P ( i , j ) \neg P(i,j) ¬P(i,j) 表示不存在皇后

思路:先保证皇后数量 ≥ N \geq N N,再添加每行、每列、每斜线不得重复的限制条件,根据抽屉原理可知去除掉了皇后数量 > N > N >N 的情况
则输出的解必定是 N N N 个皇后且满足规则约束的情况

Q 1 Q_1 Q1:每行至少存在一个元素(保证皇后 ≥ N \geq N N),每行至少一列成立 P ( i , j ) P(i,j) P(i,j)
⋀ i = 1 n ⋁ j = 1 n P ( i , j , n ) = : Q 1 \bigwedge_{i=1}^{n}\bigvee_{j=1}^{n} P(i,j,n) =: Q_1 i=1nj=1nP(i,j,n)=:Q1

Q 2 Q_2 Q2 Q 3 Q_3 Q3:每行、每列不存在重复皇后

“不重复皇后” 意味着若已存在皇后可推出该行、列不再存在皇后,可以表示为 P ( i , j ) → ¬ P ( i , j ′ ) P(i,j)\rightarrow\neg P(i,j') P(i,j)¬P(i,j) P ( i , j ) → ¬ P ( i ′ , j ) P(i,j)\rightarrow\neg P(i',j) P(i,j)¬P(i,j),其中 j ′ ≠ j , i ′ ≠ i j' \neq j, i' \neq i j=j,i=i

他们等价于 ¬ P ( i , j ) ∨ ¬ P ( i , j ′ ) \neg P(i,j)\vee\neg P(i,j') ¬P(i,j)¬P(i,j) ¬ P ( i , j ) ∨ ¬ P ( i ′ , j ) \neg P(i,j)\vee\neg P(i',j) ¬P(i,j)¬P(i,j)

于是每行、每列的不重复可以写成
⋀ i = 1 n ⋀ j = 1 n − 1 ⋀ k = j + 1 n ¬ P ( i , j ) ∨ ¬ P ( i , k ) = : Q 2 \bigwedge_{i=1}^{n}\bigwedge_{j=1}^{n-1}\bigwedge_{k=j+1}^{n} \neg P(i,j)\vee\neg P(i,k) =: Q_2 i=1nj=1n1k=j+1n¬P(i,j)¬P(i,k)=:Q2
⋀ j = 1 n ⋀ i = 1 n − 1 ⋀ k = j + 1 n ¬ P ( i , j ) ∨ ¬ P ( k , j ) = : Q 3 \bigwedge_{j=1}^{n}\bigwedge_{i=1}^{n-1}\bigwedge_{k=j+1}^{n} \neg P(i,j)\vee\neg P(k,j) =: Q_3 j=1ni=1n1k=j+1n¬P(i,j)¬P(k,j)=:Q3

Q 4 Q_4 Q4 Q 5 Q_5 Q5:每斜线不存在重复皇后

“左右斜线” 分别对应 i + j = C o n s t i+j = Const i+j=Const i − j = C o n s t i-j = Const ij=Const

在 “左下-右上斜线”中与 P ( i , j ) P(i,j) P(i,j) 相比较的元素位于 P ( i − k , j + k ) P(i-k,j+k) P(ik,j+k) 上,其中要求 i − k ≥ 1 , j + k ≤ N i-k\geq 1, j+k\leq N ik1,j+kN

在 “左上-右下斜线”中与 P ( i , j ) P(i,j) P(i,j) 相比较的元素位于 P ( i + k , j + k ) P(i+k,j+k) P(i+k,j+k) 上,其中要求 i + k ≤ N , j + k ≤ N i+k\leq N, j+k\leq N i+kN,j+kN

⋀ i = 2 n ⋀ j = 1 n − 1 ⋀ k = 1 m i n ( i − 1 , N − j ) ¬ P ( i , j ) ∨ ¬ P ( i − k , j + k ) = : Q 4 \bigwedge_{i=2}^{n}\bigwedge_{j=1}^{n-1}\bigwedge_{k=1}^{min(i-1,N-j)} \neg P(i,j)\vee\neg P(i-k,j+k) =: Q_4 i=2nj=1n1k=1min(i1,Nj)¬P(i,j)¬P(ik,j+k)=:Q4
⋀ i = 1 n − 1 ⋀ j = 2 n ⋀ k = 1 m i n ( N − i , N − j ) ¬ P ( i , j ) ∨ ¬ P ( i + k , j + k ) = : Q 5 \bigwedge_{i=1}^{n-1}\bigwedge_{j=2}^{n}\bigwedge_{k=1}^{min(N-i,N-j)} \neg P(i,j)\vee\neg P(i+k,j+k) =: Q_5 i=1n1j=2nk=1min(Ni,Nj)¬P(i,j)¬P(i+k,j+k)=:Q5

代码部分

https://github.com/CalciumArgon/N-Queen-Question-in-DPLL

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值