首页 > 编程语言 >【LeetCode】动态规划—790. 多米诺和托米诺平铺(附完整Python/C++代码)

【LeetCode】动态规划—790. 多米诺和托米诺平铺(附完整Python/C++代码)

时间:2024-10-22 11:49:42浏览次数:9  
标签:填充 790 Python 代码 多米诺 int C++ 托米 dp

动态规划—790. 多米诺和托米诺平铺

题目描述

在这里插入图片描述

前言

本文将详细讨论LeetCode上的"多米诺和三米诺平铺"问题。这是一个经典的动态规划问题,要求我们计算用多米诺骨牌和三米诺骨牌填充2x n网格的方法数。我们将从问题定义开始,逐步深入理解问题本质,提出解决方案,并给出Python和C++的具体实现。

基本思路

1. 定义

给定一个整数n,我们需要计算用1x 2的多米诺骨牌和L形的三米诺骨牌填充2 x n网格的不同方法数。结果需要对10^9 + 7取模。

2. 理解问题和递推关系

这个问题的关键在于理解如何使用动态规划来解决。我们需要找出填充方式之间的递推关系,并利用这种关系来构建解决方案。

3. 解决方法

我们可以定义dp[i]为填充2 x i网格的方法数。关键是要考虑到所有可能的填充方式:

  1. 使用一个竖直的多米诺骨牌填充最后一列:dp[i-1]
  2. 使用两个水平的多米诺骨牌填充最后两列:dp[i-2]
  3. 使用一个三米诺骨牌填充最后两列的一部分,这有两种方式

因此,我们可以得到递推公式:
dp[i] = dp[i-1] + dp[i-2] + 2 * (dp[i-3] + ... + dp[0])

4. 进一步优化

我们可以通过数学推导简化上述公式。令S[i] = dp[i-3] + ... + dp[0],那么:
S[i] = S[i-1] + dp[i-3]
dp[i] = dp[i-1] + dp[i-2] + 2 * S[i]

这样,我们可以在O(1)时间内计算每个状态,将时间复杂度优化到O(n)。

5. 小总结

通过分析填充方式并建立递推关系,我们成功地将问题转化为了一个动态规划问题。通过数学推导,我们进一步优化了算法的时间复杂度。

以上就是多米诺和托米诺平铺问题的基本思路。


代码实现

Python代码

class Solution:
    def numTilings(self, n: int) -> int:
        MOD = 10**9 + 7
        if n <= 2:
            return n
        #初始化dp数组
        dp = [0] * (n + 1)
        dp[0], dp[1], dp[2] = 1, 1, 2
        
        # 初始化S
        S = 1
        
        # 动态规划过程
        for i in range(3, n + 1):
            dp[i] = (dp[i-1] + dp[i-2] + 2 * S) % MOD
            S = (S + dp[i-2]) % MOD
        
        return dp[n]

在这里插入图片描述

Python代码解释总结

这段Python代码实现了优化后的动态规划算法。我们使用dp数组存储每个状态的解,使用S变量来存储优化后的累加和。通过一次遍历,我们可以在O(n)的时间复杂度内求解问题。代码中的取模操作确保了结果在给定范围内。

C++代码

class Solution {
public:
    int numTilings(int n) {
        const int MOD = 1e9 + 7;
        if (n <= 2) return n;
        
        // 初始化dp数组
        vector<long long> dp(n + 1, 0);
        dp[0] = 1; dp[1] = 1; dp[2] = 2;
        
        // 初始化S
        long long S = 1;
        
        // 动态规划过程
        for (int i = 3; i <= n; ++i) {
            dp[i] = (dp[i-1] + dp[i-2] + 2 * S) % MOD;
            S = (S + dp[i-2]) % MOD;
        }
        
        return dp[n];
    }
};

在这里插入图片描述

C++代码解释总结

C++代码的实现逻辑与Python版本相同,都是基于优化后的动态规划算法。使用vector<long long>来存储dp数组,以避免整数溢出。同样通过一次遍历完成所有状态的计算,时间复杂度为O(n)。

总结

通过本文的分析和实现,我们深入理解了"多米诺和三米诺平铺"问题的本质,并学习了如何使用动态规划来解决此类组合问题。我们不仅给出了基本的解决方案,还通过数学推导对算法进行了优化,最终得到了时间复杂度为O(n)的高效解法。Python和C++的实现展示了如何将理论转化为实际代码,这对于理解和掌握动态规划技巧很有帮助。

标签:填充,790,Python,代码,多米诺,int,C++,托米,dp
From: https://blog.csdn.net/AlbertDS/article/details/143145244

相关文章

  • P5690 [CSP-S2019 江西] 日期 &&P7909 [CSP-J 2021] 分糖果 &&P5657 [CSP-S2019] 格雷
    今天继续懒惰,继续三合一!!![CSP-S2019江西]日期题目背景CSP-SJX2019T1题目描述Alice在纸上写下了一个日期,形式为\(\text{MM-DD}\),其中\(\text{MM}\)与\(\text{DD}\)都是两位数字,分别表示月和天,然而这个日期并不一定存在。Alice找来了Bob要他更改若干位上的数字,使得这个......
  • BIOE7902 Event Detection
    BIOE7902–Assignment2–EventDetectionThegoalofthisassignmentistoreproducetheresultsofthispaperascloseaspossible:RaúlAlonsoÁlvarez,ArturoJ.MéndezPenín,X.AntónVilaSobrino-AComparisonofThreeQRSDetectionAlgorithmsOver......
  • A 4nm 6163-TOPS/W/b 4790-TOPS/mm2/b SRAM Based Digital-Computing-in-Memory Macro
    SRAMarray和Localadder耦合在一起形成一个块,两个块share一个semi-global-adder,四个块再去shareGlobaladder和移位累加器。这样的floorplan使得整体结构上不存在一大块独立的巨型多级加法树,使得布局变得更加的规整。这里讨论了mix-Vt设计的问题,即混用高Vt管子和低Vt管子,高Vt......
  • 力扣 | 一维简单线性dp | 2140. 解决智力问题、322. 零钱兑换、2466. 统计构造好字符
    文章目录一、2140.解决智力问题二、322.零钱兑换三、2466.统计构造好字符串的方案数四、91.解码方法五、983.最低票价六、790.多米诺和托米诺平铺需要特别注意的题目有2140.解决智力问题和983.最低票价,因为这两个题目可以启发思路,其他的题都比较普通。一、21......
  • Debian12 AMD 显卡 7900XT 安装使用 stable-diffusion-webui 笔记
    简介由于AMD官方没有提供Debian12的驱动和ROCM,只好安装Ubuntu20.04的驱动和ROCM,必要软件git和python3-venv。添加i386仓库sudodpkg--add-architecturei386&&\sudoaptupgrade-y&&\aptupgrade-y下载驱动安装程序到AMD官网下载Ubuntu20.04驱动......
  • nvidia&QM9700&9790 ib NDR交换机FAQ
    一、交换机简介:基于NVIDIAquantum-2的QM9700和QM9790交换系统提供64个逻辑端口,在1U标准机箱设计中,每个逻辑端口400Gb/sib,支持32个800G/sOSFP光模块,支持最新的NDR技术,NVIDIAQuantum-2带来了一个高速、极低延迟和可扩展的解决方案,其中包含最先进的技术,如远程直接内存访问(RD......
  • CSP历年复赛题-P7909 [CSP-J 2021] 分糖果
    原题链接:https://www.luogu.com.cn/problem/P7909题意解读:计算L~R之间数模n的最大值。解题思路:如果你考虑枚举L~R,每个数模n,然后求max,那么就超时了,肯定有一点小技巧在里面。我们知道,一个数%n,最大值是n-1不难考虑,如果R/n和L/n的的商是一样的,而R>=L,那么说明R%n>=L%n,那么此时最大......
  • 打卡信奥刷题(52)用Scratch图形化工具信奥P7909 [普及组] [CSP-J 2021] 分糖果
    [CSP-J2021]分糖果题目背景红太阳幼儿园的小朋友们开始分糖果啦!题目描述红太阳幼儿园有nnn个小朋友,你是其中之一。保证......
  • 使用git报错:error: RPC failed; curl 18 transfer closed with outstanding read data
    今天在使用git下载项目时发生报错:error:RPCfailed;curl18transferclosedwithoutstandingreaddataremainingerror:4790bytesofbodyarestillexpectedfatal:earlyEOFfetch-pack:unexpecteddisconnectwhilereadingsidebandpacketfatal:fetch-pack:in......
  • P7903 兜心の顶(构造)
    P7903兜心の顶题目背景Source:八仙敬酒吕洞宾——醉酒提壶力千钧;铁拐李——旋肘膝撞醉还真;汉钟离——跌步抱坛兜心顶;蓝采和——单提敬酒拦腰破;张果老——醉酒抛杯踢连环;曹国舅——仙人敬酒锁喉扣;韩湘子——擒腕击胸醉吹箫;何仙姑——弹腰献酒醉荡步。题目描述给定正......