zoukankan      html  css  js  c++  java
  • Mondriaan's Dream

    poj2411:http://poj.org/problem?id=2411

    题意:给你1*2的方块,让你把n*m的房间填好有多少种方式。

    题解:状压dp。这一题,我是不会做了,看懂了题解之后,震惊了。这Dp只要找对状态方程,简直就是一种艺术啊。我深深的喜欢上DP了。好了。讲讲这一题吧。首先是状态方程f[i][j]表示第i行第j个状态所得的方案数。j有3种形式,如果出现1,那么1表示这一行会放一个竖的,0表示不放,00表示横着放一块。并且用f[i][0]表示第i行什么都不放。好了,然后是枚举状态了。对于本行的 状态s1和上一行状态上s2来说,如果s1&s2>0的话,说明肯定存在一位,在这一位上上一行竖着放着一个,这一行应该是不放,但是这一位放了一个,显然这样的状态是不合理的。然后没有这样的状况的话,就要检查剩余的0是否两个两个连续,如果有多余0不是一对说明,这两行在这一位是空着的,这样也是不合理,因为这一位的两个空格,下一行是没有办补充上来的。这里最巧妙的就是用f[i][0]表示什么都不放,那么最终的答案就是f[n+1][0],而且初始化的话f[1][0]=1,这也是显然的。有了这些还有一些特判,如果n*m%2==1说明面积是奇数,但是面积不可能是奇数,所以不可能拼完。还有一个重要的地方就是(n<m),swap(n,m);这里还没有弄懂,但是不交换的话,答案就不对。

     1 #include<iostream>
     2 #include<cstdio>
     3 #include<cstring>
     4 #include<algorithm>
     5 using namespace std;
     6 int n,m;
     7 long long f[13][1300];
     8 bool judge(int s1,int s2){
     9     if(s1&s2)return 0;
    10     s1|=s2;
    11     for(int i=0;i<m;){
    12         int j=(s1&(1<<i));
    13         if(j==0){
    14             if(i==m-1)return 0;
    15             else if((s1&(1<<(i+1)))!=0)return 0;
    16             i+=2;
    17         }
    18         else i++;
    19     }
    20     return 1;
    21 }
    22 int main(){
    23    while(~scanf("%d%d",&n,&m)&&n){
    24       memset(f,0,sizeof(f));
    25       if(n*m&1){
    26         printf("0
    ");
    27         continue;
    28       }
    29       f[1][0]=1;
    30       if(n<m)swap(n,m);
    31       for(int i=1;i<=n;i++){
    32         for(int j=0;j<(1<<m);j++){
    33             for(int k=0;k<(1<<m);k++){
    34                 if(judge(j,k)){
    35                     f[i+1][j]+=f[i][k];
    36                 }
    37             }
    38          }
    39       }
    40      printf("%I64d
    ",f[n+1][0]);
    41    }
    42 }
    View Code
  • 相关阅读:
    6、redux源码解析
    5、redux源码解析
    4、redux源码解析
    3、redux码源
    2、redux源码探索
    1、redux源码探索
    Second Autoprefixer control comment was ignored. Autoprefixer applies control comment to whole block, not to next rules.
    Linux命令——whereis
    Linux命令——which
    Linux命令——tail
  • 原文地址:https://www.cnblogs.com/chujian123/p/3874056.html
Copyright © 2011-2022 走看看