// 題意:乙個n*m的矩陣,求用i型(1 * 2)和l型的兩種方塊進行填滿有多少種方法
// 方法:這題和poj2411有點類似 做過方塊填充的應該都認得出來要用狀壓
// 但是要比poj2411複雜 思路也是類似 不過因為要考慮l型 情況也複雜的多
// 語文有點不太好 可能有點說不清楚
// 利用兩個引數 b1 表示前面的放置方式對now(當前行狀態)的當前列的影響,b2 表示對pre(上一行狀態)的當前列的影響
// 有影響為1 沒影響為0 其實可以這麼理解 如果為1就代表有方塊從左邊凸出來會占用當前列 為0就代表沒有凸出來
// 這裡我提出一些自己遇到的問題
// 首先列舉當前狀態和上一狀態要分成兩種情況考慮
// 不僅要考慮b1,b2 還要考慮從下往下凸出來的這種情況,就是上一行的上一行有方塊凸下來占用上一行 說起來有點繞
// 舉個例子 如果當前 b1 == 0 && b2 == 0
// 那麼這一列我們可以這麼放
// 1 1 1 1 1 1
// 或者 或者 或者 (這四種是上一行的上一行沒有從上往下凸出來的方塊的放置方法)
// 1 1 1 1 1
// 1
// 或者 或者 不放 (這三種是上一行的上一行有從上往下凸出來的方塊的放置方法)
// 1 1 1 1
// 上面總共7種 上面的每種都滿足把上一行的當前列填滿了 只不過是分為是由左邊凸出來的 和 上面凸出來的
// 填滿我起初也有疑問為什麼下面的這三種放置也可以
// 語文果然不太好 看下面幾張圖一定有用
// 一 二 三 四 五 六
// 1 1 1 1 1 1 1
// 1 1 1 1 1 1 1 1 1
void dfs(int line, int k, int now, int pre, int b1, int b2)
if(!b1 && !b2)
else if( b1 && !b2)
else if(!b1 && b2)
else
}int main()
{ memset(ans, 0, sizeof ans);
memset(dp, 0, sizeof dp);
while(cin>>n>>m)
{if(ans[n][m]){
cout<
SGU 131 狀態壓縮dp
include include include include include include include include include include include include includeusing namespace std ifdef win32 define i64 int6...
SGU 223 國王 狀壓DP
在 n n n n 的棋盤上放 k k k 個國王,國王可攻擊相鄰的 8 8 8 個格仔,求使它們無法互相攻擊的方案總數。n n 狀壓dp是一種比較暴力的dp。n n 首先dp i j k 表示前i行放置k個國王,且當前行狀態是j的方案數。n n 轉移方程 dp i j k dp i 1 m k s...
狀壓dp(總結)狀態壓縮
狀壓這個和二進位制分不開關係 所以,對於二進位制的熟悉是必不可少的技能 與操作,1不變,0變0 或操作,0不變,1變1 異或操作,0不變,1取反 取反操作,把每乙個二進位制位0變1,1變0 還有一些複雜操作可以根據這些去理解 狀態壓縮 所謂狀態壓縮就是把dp的每一次轉移時的狀態用二進位制來表示 或者...