2 SAT問題的演算法

2022-08-05 11:33:11 字數 1097 閱讀 5180

求解2-sat問題的演算法有很多,有一種效率還不錯,實現方便又理解方便的演算法。

注意例子中的那個條件“x1為假或x2為真”,在x1為假的時候x2可以為任意值,但在x1為真的時候,x2為滿足條件必須是真。也就是說x1為真可以推匯出x2為假、x2為假可以推匯出x1為真。換成一般的情況,已知xa→xb',則xb→xa'、已知xa'→xb,則xb'→xa(xi表示真xi'表示假)這個稱為對稱性,仔細理解下,下面證明會用到這個結論。

我們通常建一個圖g,圖中節點數量為2n,把節點標號,2i節點代表著xi、2i+1代表xi'。如果xi為真的時候標記節點2i,為假的時候標記2i+1。如果知道xa→xb',則加入一條有向邊2a→2b+1,同時得到xb→xa',再加入一條邊2b→2a+1。

列舉2i和2i+1都沒有標記的節點,先假設xi為真,給2i標記,再進行dfs遍歷,把所有可以到達的點都標記,標記過程中如果出現某個點2x和2x+1都被標記,因為不會存在x同時為真和假的情況,所以xi不能為真。再假設x2為假,給2i+1標記重複上述過程。如果xi值為真和假時都不可以,則此題無解。

修改之前的變數可以不可以讓正在列舉的點可以為真或假?答案是不可以。因為假設某個節點a被標記,dfs時遍歷到a'發現矛盾,則有條路可以從i走到a’,根據對稱性,a有條路可以走到i,i就不是2i和2i+1都沒有被標記的節點,矛盾,所以不存在這種情況。所以dfs遍歷到的點要麼是已經標記過的點或者2i和2i+1都未標記的點,與之前的變數無關,所以2-sat演算法正確。

偽**:

bool dfs(int x){

____如果x節點被標記,返回真

____如果x^1節點被標記,返回假

____u為x可以到達的所有節點

________如果dfs(u)為假,返回假

____返回真

bool solve(){

____for i=1 to n

________

如果2i和2i+1都為標記

____________

如果dfs(2i)為假

________________

清除上次遍歷的節點的標記 //實現時可以用棧

________________

如果dfs(2i+1)為假,返回假

____返回真

2 SAT演算法(未完)

例題 演算法 演算法所求問題 這個演算法主要是求有n個人,每個有m個要求,要求只可能是1或0的情況 及是或不是,要或不要 ,且每個要求只需滿足其一即可,求是否有可行的分配方案 當然,也可以求出那個可行的分配方案 演算法前置知識 tarjan求強連通分量,拓撲序 演算法主要思路 如何求出能否有一種方案使得所有人...

2 SAT問題及其演算法

2 sat問題 現有一個由n個布林值組成的序列a,給出一些限制關係,比如a x and a y 0 a x or a y or a z 1等,要確定a 0 n 1 的值,使得其滿足所有限制關係。這個稱為sat問題,特別的,若每種限制關係中最多隻對兩個元素進行限制,則稱 為2 sat問題。 由於在2 ...

演算法學習筆記 2 SAT

sat 是適定性 satisfiability 問題的簡稱。一般形式為 k 適定性問題,簡稱 k sat。而當 k 2 時該問題為 np 完...