一:论语
二:题目
三:上码
class Solution {
public:
/**
思路:1.分析题意
这个就是我们从coins数组中找出几个数字(可以重复)然后的话我们是需要找出这个几个数字的和为amount;
那么这个满足答案的结果是可以有多个,但是我们的要求是求取最少的硬币个数
2.动态规划五步走
1>:确定dp数组的含义以及下标的含义
dp[j] 表示背包容量为j(也就是金额为j)的时候;我们最少为dp[j]个数字
2>:确定dp数组的状态递推公式
dp[j] = min(dp[j],dp[j-coins[i]]+1);//加这个1代表的是我们加上了coins[i]这个数字
3>:确定dp数组的初始化
因为这里我们是要求最小的值;所以我们是需要在和初始化的时候将其dp初始为最大值
但是当j = 0的时候 也就是背包容量为0的时候我们需要赋初值为0;根据题目中最后一个例子我们
可以得出;
4>:确定dp数组的遍历顺序
因为可以重复加入,所以的话我们是正序
5>:举例验证
coins = [1,2,5];amount = 6
0 1 2 3 4 5 6
coins[0] = 1 0 1 2 3 4 5 6
coins[1] = 2 1 1 1 2 3 4 5
coins[2] = 5 1 1 1 2 3 4 2
*/
int coinChange(vector<int>& coins, int amount) {
vector<int> dp(amount+1,INT_MAX);
dp[0] = 0;
for(int i = 0; i < coins.size(); i++) {//物品
for(int j = 0; j <= amount; j++) {//背包容量
if(j >= coins[i] && dp[j-coins[i]] != INT_MAX)//如果我们的第一个物品的价值不是1的话,那么我们
dp[j] = min(dp[j],dp[j-coins[i]] + 1); //对应的dp[j]就是无穷大的,所以我们是不能取其值的
}
}
return dp[amount] == INT_MAX ? -1 : dp[amount];//这个用3目运算符目的是为了当有不满足tiao件的时候
} // 我们返回-1
};