790.多米诺和托米诺平铺(简单动态规划)

 

输入: n = 3
输出: 5
解释: 五种不同的方法如上所示。

 

示例 2:

输入: n = 1
输出: 1

提示:

  • 1 <= n <= 1000

 思路:

题目比较晦涩难懂,大致意思就是用这两种类型的块去填满一个2*n的块,保证每一列,都是被填充的。

这道题使用动态规划的方法,在遍历的过程中,将遍历中的状态存储下来,方便接下来的遍历可以在之前存储的状态基础上得到当前的状态。

这里对于某一列i,其存在四中状态

1.整列为空,记为状态0

2.第一个方格被覆盖,记为状态1

3.第二个方格被覆盖,记为状态2

4.两个方格都被覆盖,记为状态3

 

我们使用一个数组dp[i][state]来表示用瓷砖将第i列铺成状态state的所有方法

  • 如果第i列的状态为0,记第i列为空,这时候和第i-1列为满(状态3)的情况一样,即dp[i][0]=dp[i-1][3].
  • 如果第i列的状态为1,想要变成这种状态则有两种情况。

 即有dp[i][1]=dp[i-1][0]+dp[i-1][2]

  • 如果第i列的状态为2,也存在两种情况。

 即dp[i][2]=dp[i-1][0]+dp[i-1][1]

  • 如果第i列的状态为3,则存储下面四种情况

 综上所述,状态转移方程就列出来了。

考虑到特殊情况

当i=0,考虑第0层的状态时,i-1会越界,因此把第0层作为一个初始化层。从1开始计算。

dp[0][0]=0(没有砖),dp[0][1]=0,dp[0][2]=0(无法铺出这两种形状);dp[0][3]=1,可以竖着铺一个多米诺瓷砖。

 最后的结果就是dp[n][3]

代码:

class Solution {
public:
    const long long mod= 1e9+7;
    int numTilings(int n) {
        long long dp[1002][4];
        for(int i=0;i<n;i++){
              for(int j=0;j<4;j++){
                    dp[i][j]=0;
              }
        }
        dp[0][3]=1;
        for(int i=1;i<=n;i++){
            dp[i][0]=(dp[i-1][3])%mod;
            dp[i][1]=(dp[i-1][0]+dp[i-1][2])%mod;
            dp[i][2]=(dp[i-1][0]+dp[i-1][1])%mod;
            dp[i][3]=(dp[i-1][0]+dp[i-1][1]+dp[i-1][2]+dp[i-1][3])%mod;
        }
        return dp[n][3];
    }
};

 

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值