LeetCode零钱兑换(dp)

题目描述

用coins = [1, 2, 5], amount = 11举例

组成11的硬币数,考虑最后一枚硬币是1、2、5,可以分3种情况:

  • 最后一枚硬币是1元:num1 = 【组成10的最小硬币数】+ 1(1枚1元硬币)
  • 最后一枚硬币是2元:num2 = 【组成9的最小硬币数】+ 1(1枚2元硬币)
  • 最后一枚硬币是5元:num3 = 【组成6的最小硬币数】+ 1(1枚5元硬币)

综合上述3种情况,组成11的最少硬币数就是min(num1, num2, num3)

动态规划思想在于先解决小问题,解决大问题的时候直接使用小问题的结论进行解决。为此我们有一个for循环,当前兑换金额cur从1到最终的amount递增,先考虑总金额较小时,需要最少的硬币数

int coinChange(vector<int>& coins, int amount) {
    
    
        vector<int> dp(amount+1 , -1);
        dp[0] = 0;//0元钱最少需要0个硬币
        for(int cur = 1; cur <= amount; cur++){
    
    
            dp[cur] = amount + 1; //只要有面值为1的硬币,就可以兑换成功,最多使用amount个硬币。否则将硬币数量设为amount + 1 表示当前金额cur无法兑换
            for(int coin : coins){
    
    //此循环完成后就相当于上述解析种的min(num1, num2, num3)完成
                if(cur >= coin){
    
    
                    dp[cur] = dp[cur-coin] + 1 < dp[cur] ? dp[cur-coin] + 1 : dp[cur];
                }
            }
        }
        return dp[amount] == amount + 1 ? -1 : dp[amount];
    }

在这里插入图片描述
参考题解

猜你喜欢

转载自blog.csdn.net/qq_42500831/article/details/105466078
今日推荐