每日一道Leetcode- 1420. 生成数组 【动态规划】

在这里插入图片描述
看别人的解法,强大!
在这里插入图片描述

class Solution:
    def numOfArrays(self, n: int, m: int, k: int) -> int:
        # 长度为n 数组中每个元素范围:[1,m] 
        # 使得找到最大值的搜索代价小于k
        # 生成这样的数组 相当于最大值要在数组中的前k个
        # dp[n][i][k] n:长度 i:m的可选值 k:serach_cost
        def cal(n,i,k):
            if dp[n][i][k] != -1:
                return dp[n][i][k]
            if n==0 or k == 0 or i == 0:
                dp[n][i][k] = 0
                return 0
            if n == 1 and k == 1:
                dp[n][i][k] = 1
                return 1
            # j 取 [1,i-1] 最大值出现在数组末尾,前n-1个元素都小于i,只需要把前n-1维数组的情况相加即可,变化【j】的位置,加起来
            r = 0
            for j in range(1,i):
                r += cal(n-1,j,k-1)
                r %= 1000000007
            # j 取 i , 最大值出现在前n-1位中,数组末尾的元素可以从1-i中选,i种情况呗
            r += cal(n-1,i,k)*i
            r %= 1000000007
            dp[n][i][k] = r
            return r

        dp = [[[-1 for _ in range(k+1)] for _ in range(m+1)] for _ in range(n+1)] 
        # dp[0][i][k] = dp[n][0][k] = dp[n][i][0] = 0
        
        r = 0
        for i in range(1,m+1):
            # 对于不同i
            r += cal(n,i,k)
            r %= 1000000007
        return r
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值