代码随想录第四十一天 动态规划 Part3 ● 343. 整数拆分 ● 96.不同的二叉搜索树

动态规划 Part3
  •  343. 整数拆分

题目链接:. - 力扣(LeetCode)

刚看到这道题是没有思路的,看了卡哥的思路,这里其实有个规律,就是尽可能拆分出相同的数才会使乘积最大;这里定义 dp[i]是对 i 进行拆分,得到的最大乘积;

那么会有两种情况,一种是拆分两次即得到了最大乘积:i * (j-i), 一种是拆分三次及以上会得到最大乘积:及 j * dp[i - j] 这里不对 j 进行拆分是因为对 j 拆分的情况会在 dp[i-j]中已经包括了;除此之外,还要对比 dp [i]和前两者的大小,因为在每次拆分的时候,如果 dp [i]已经是最大则无需拆分

var integerBreak = function(n) {
    let dp = new Array(n + 1).fill(0) //定义否则 Math.max可能为 NaN
     dp[2] = 1

    for(let i = 3; i <= n; i = i + 1) {
        for(let j = 1; j < i - 1; j = j + 1) {
            dp[i] = Math.max(j * (i - j), j * dp[i - j], dp[i])
        }
    }
    return dp[n]
};
  •  96.不同的二叉搜索树 

题目链接:. - 力扣(LeetCode)

二叉搜索树定义

1. 若左节点不为空,则左子树上子节点值均小于根节点的值

2. 若右节点不为空,则右子树上子节点值均大于根节点的值

3. 左右子树也分别为二叉搜索树

这里需要探索递增的规律

对于 n = 3来说,以 1 和 3 为头节点的二叉树,子节点和 n=2的二叉树的形态一样,

对于n = 3的的二叉树的二叉树个数为 dp[2] * dp[0] + dp[1] * dp[1] + dp[0] * dp[2], 对于二叉搜索树来说,

这里 d[i]为有 i 个节点时,二叉搜索树的个数

如果头节点为 j 的话,那么左子树节点个数为 j - 1 个,因为左子树上节点的数值都小于头节点,右子树的节点的个数为 i- j, 因为右子树的节点的数值都大于头节点,那递推公式即为 dp[j] = dp[j- 1] + dp[i - j]

初始化 dp[0] = 1, dp[1] = 1如果 dp[0]为 0 的话,乘积则还是 0

代码如下

var numTrees = function(n) {
     let dp = new Array(n + 1).fill(0)
    dp[0] = 1, dp[1] = 1
    for(let i = 2; i <= n; i = i + 1) {
        for(let j = 1; j <= i ; j = j + 1) {
            dp[i] += dp[j-1] * dp[i -j]
        }
    }
    return dp[n]
};

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值