hdu1400Mondriaan's Dream

这是一道很好的题目,我不会做,所以答案是从网上弄的。

把人家的代码又重新写了一遍,发现他的也是错的——可能跟编译器有关,但是为什么提交的时候可以通过呢???神奇

就因为dp[i][j]这个错了

通过的代码

#include<iostream>
#include<cstring>
using namespace std;
const int mm=1<<13;
long long dp[14][mm];
int w,h;
bool line_one(int x)
{
    for(int i=0;i<w;)
    if((x&(1<<i))>0)
    {
        if(i==w-1||(x&(1<<(i+1)))==0)
        return 0;
        i+=2;
    }else i++;
    return 1;
}
bool trans(int a,int b)
{
    for(int i=0;i<w;)
    {
        if((a&(1<<i))>0)
        {
            if((b&(1<<i))==0)i++;
            else if(i==w-1||(a&(1<<(i+1)))==0||(b&(1<<(i+1)))==0)return 0;
            else i+=2;
        }
        else if((b&(1<<i))>0)i++;
        else return 0;
    }
    return 1;
}
int main()
{
    while(cin>>w>>h)
    {
        if(w==0&&h==0)break;
        if(w>h){int zz=w;w=h;h=zz;}
        int z=1<<w;
        for(int i=0;i<z;i++)
        if(line_one(i))///判断一层状态合法
        dp[1][i]=1;
        for(int i=2;i<=h;i++)
        {
            for(int j=0;j<z;j++)
            { dp[i][j]=0;
             for(int k=0;k<z;k++)
             if(trans(k,j))///判断k状态能否转化到j状态
             dp[i][j]+=dp[i-1][k];
            }
        }

        cout<<dp[h][z-1]<<"\n";
    }
}

 

 

转载于:https://www.cnblogs.com/dowson/p/3302503.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值