日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

2-SAT

發布時間:2024/4/18 编程问答 38 豆豆
生活随笔 收集整理的這篇文章主要介紹了 2-SAT 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

2-Satisfiability

2可滿足性,2-SAT或僅2SAT是將值賦值給變量的計算問題,每個變量具有兩個可能的值,以滿足變量對的約束系統。這是一般布爾可滿足性問題的一個特例,它可能涉及對兩個以上變量的約束,以及約束滿足問題,這可以允許對每個變量的值進行兩次以上的選擇。但與NP完全的那些更一般的問題形成對比,可以在多項式時間內求解2-可滿足性。

個人理解

多個約束條件每個約束有兩個限制,判斷是否存在滿足所有條件的合理解

思路

對于這樣的一組限制 AAABBB不能同時存在,我們可以轉化成滿足AAA的條件下BBB就不能滿足,對應建圖的時候我們把每個點拆成兩個情況or不選,根據情況建邊

1.是否存在解

hihoCoder #1467
Tarjan縮點,如果一個強連通分量里面存在矛盾(一個點選和不選同時存在)就不存在解

2.求一個字典序最小的解

hihoCoder #1468
暴力DFS O(NMNMNM)
首先SAT建邊,然后對于每個點先從小的序號DFS,之后判斷標記的點中是否存在矛盾,如果拆成的兩個點都存在矛盾,那就無解

vector<int> g[maxn]; int vis[maxn], temp[maxn], len;int other(int x) {return (x & 1) ? x+1 : x-1; }int dfs(int x) {if (vis[other(x)]) return 0;if (vis[x]) return 1;temp[len++] = x;vis[x] = 1;for (int i = 0, y; i < (int)g[x].size(); ++i) {y = g[x][i];if (dfs(y) == 0) return 0;}return 1; }int Twosat() {for (int i = 1; i <= n; ++i) {if (vis[i*2] || vis[i*2-1]) continue;if (dfs(i*2-1) == 0) {for (int j = 0; j < len; ++j) {vis[temp[j]] = 0;}len = 0;if (dfs(i*2) == 0) {return 0;}}}return 1; }if (Twosat()) {for (int i = 1; i <= n; ++i) {if (vis[i*2-1]) cout << "R";else cout << "B";}cout << endl; }else cout << -1 << endl;

總結

以上是生活随笔為你收集整理的2-SAT的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。