求把\(N*M(1\le N,M \le 11)\) 的棋盘分割成若干个\(1\times 2\) 的长方形,有多少种方案。例如当 \(N=2,M=4\)时,共有5种方案。当\(N=2,M=3\)时,有3种方案。

NM只有11,八九不离十可以状压了,反正得挨个铺,所以从上到下考虑。假如现在铺好了前\(i\) 层,基本思想就是从\(i\) 层的状态转移到\(i+1\)层的状态。但是该如何表示?观察一下铺满第 \(i\) 层的样子(必须保证第\(i\)层是满的,也就是说有的可以凸出来到\(i+1\)层但是要保证\(i\)层是满的)

对于第 i 行中竖着放的,第 \(i+1\) 层要受到牵连,它必须补全竖着放置的上一半才行。但对于横着放的,第\(i+1\)层则无所谓。

所以我们可以用二进制中的 1 来表示他是否是竖着放置的上一半。为0则为其他状况。

\(d[i][j]\)表示第 \(i\) 的形态为\(j\) 时,前\(i\) 行分割方案的总数。 \(j\) 是用十进制整数记录的 \(m\) 位二进制数。考虑\(i+1\)行的状态\(k\)在满足什么情况下转移是合法的。

  • \(j\)中为 1 的位,\(k\)中必须为0
  • \(j\)中为 0 的位,\(k\)中可以为1,但 k 要是为 0,就必须是连续的偶数个0(想一想为什么)

    对于第一条,可以用 \(i\&j = 0\) 来判断,对于第二条,有\(z = i|j\),那么 z 的二进制表示中,每一段连续的 0 都必须有偶数个。(这些0代表若干个横着的 \(1\times 2\) 长方形,奇数个0无法分割成这种形态。
#include <iostream>
#include <cstdio>
using namespace std;
int n,m;
long long f[12][1<<11];
bool in_s[1<<11]; int main(){
while(cin>>n>>m && n){
//先把合法状态筛出来,即二进制表示中每一段连续的0都有偶数个
for(int i=0;i<1<<m;i++){
bool cnt = 0,has_odd = 0;
for(int j=0;j<m;j++)
if(i >> j & 1)has_odd |= cnt,cnt=0;
else cnt ^= 1;
in_s[i] = (has_odd | cnt) ? 0 : 1;
}
f[0][0] = 1;
for(int i=1;i<=n;i++){
for(int j=0;j<1<<m;j++){
f[i][j] = 0;
for(int k=0;k< 1<<m;k++){
if((j & k) == 0 && in_s[j|k])
f[i][j] += f[i-1][k];
}
}
}
cout<<f[n][0]<<endl;
}
return 0;
}

POJ-2411 Mondriann's Dream (状压DP)的更多相关文章

  1. POJ 2411 Mondriaan's Dream -- 状压DP

    题目:Mondriaan's Dream 链接:http://poj.org/problem?id=2411 题意:用 1*2 的瓷砖去填 n*m 的地板,问有多少种填法. 思路: 很久很久以前便做过 ...

  2. POJ 2411 Mondriaan's Dream ——状压DP 插头DP

    [题目分析] 用1*2的牌铺满n*m的格子. 刚开始用到动规想写一个n*m*2^m,写了半天才知道会有重复的情况. So Sad. 然后想到数据范围这么小,爆搜好了.于是把每一种状态对应的转移都搜了出 ...

  3. Poj 2411 Mondriaan's Dream(状压DP)

    Mondriaan's Dream Time Limit: 3000MS Memory Limit: 65536K Description Squares and rectangles fascina ...

  4. POJ 2411 Mondriaan'sDream(状压DP)

    题目大意:一个矩阵,只能放1*2的木块,问将这个矩阵完全覆盖的不同放法有多少种. 解析:如果是横着的就定义11,如果竖着的定义为竖着的01,这样按行dp只需要考虑两件事儿,当前行&上一行,是不 ...

  5. [poj2411] Mondriaan's Dream (状压DP)

    状压DP Description Squares and rectangles fascinated the famous Dutch painter Piet Mondriaan. One nigh ...

  6. POJ 1185 炮兵阵地(状压DP)

    炮兵阵地 Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 26426   Accepted: 10185 Descriptio ...

  7. poj 2288 Islands and Bridges ——状压DP

    题目:http://poj.org/problem?id=2288 状压挺明显的: 一开始写了(记忆化)搜索,但一直T: #include<iostream> #include<cs ...

  8. 【POJ 2923】Relocation(状压DP+DP)

    题意是给你n个物品,每次两辆车运,容量分别是c1,c2,求最少运送次数.好像不是很好想,我看了网上的题解才做出来.先用状压DP计算i状态下,第一辆可以运送的重量,用该状态的重量总和-第一辆可以运送的, ...

  9. POJ 1185 炮兵阵地 (状压DP)

    题目链接 题意 : 中文题不详述. 思路 :状压DP,1表示该位置放炮弹,0表示不放.dp[i][j][k],代表第 i 行的状态为k时第i-1行的状态为 j 时放置的最大炮弹数.只是注意判断的时候不 ...

随机推荐

  1. Windows下如何玩转火热的go-zero

    作者:阿啄debugIT 前言 go-zero 是一个集成了各种工程实践的 web 和 rpc 框架.通过弹性设计保障了大并发服务端的稳定性,经受了充分的实战检验. go-zero 包含极简的 API ...

  2. LeetCode561 数组拆分 I

    给定长度为 2n 的数组, 你的任务是将这些数分成 n 对, 例如 (a1, b1), (a2, b2), ..., (an, bn) ,使得从1 到 n 的 min(ai, bi) 总和最大. 示例 ...

  3. 网络之HTTPS

    文章目录 HTTPS的基本概念 HTTP和HTTPS的区别 HTTPS的优点 对称加密和非对称加密 对称加密 非对称加密 HTTPS采用的加密方式 认证 证书的组成 使用openssl怎么制造证书 H ...

  4. 【Linux】Linux介绍和安装 - 测试题

    第一部分测试题 Linux介绍和安装 测试题 做点练习题,巩固一下咯~ ~ _ 10 个选择题. 1.让我们选择开机时进哪个操作系统的软件叫什么? A. booter B. bootloader C. ...

  5. Upload - Labs (上)

    Pass - 01: 1.尝试上传一个php文件:aaa.php,发现只允许上传某些图片类型,用bp抓包,发现http请求都没通过burp就弹出了不允许上传的提示框,这表明验证点在前端,而不在服务端 ...

  6. Eclipse中给jar包导入JavaDoc的方法

    原文转载自:http://blog.csdn.net/mr_von/article/details/7740138 在使用Java语言开发的过程中,开发人员经常需要用到一些开源的工具包.在使用别人的j ...

  7. [Usaco2007 Jan]Telephone Lines架设电话线

    题目描述 FarmerJohn打算将电话线引到自己的农场,但电信公司并不打算为他提供免费服务.于是,FJ必须为此向电信公司支付一定的费用.FJ的农场周围分布着N(1<=N<=1,000)根 ...

  8. 前端知识(二)05-Eslint语法规范检查-谷粒学院

    目录 一.ESLint简介 二.启用ESLint 1.ESLint插件安装 2.插件的扩展设置 3.确认开启语法检查 三.ESLint规则说明 1.规则说明 2.语法规则 一.ESLint简介 ESL ...

  9. 在nodejs中创建child process

    目录 简介 child process 异步创建进程 同步创建进程 在nodejs中创建child process 简介 nodejs的main event loop是单线程的,nodejs本身也维护 ...

  10. Tensorflow-基础使用

    Tensorflow基本概念 使用图(graphs)来表示计算任务 在被称之为会话(Session)的上下文(context)中执行图 使用tensor表示数据 通过变量(Variable)维护状态 ...