【发布时间】:2015-09-02 05:38:08
【问题描述】:
给定一个 N 值,如果我们想找 N 美分,并且我们有无限供应 S = { S1, S2, .. , Sm} 价值的硬币,我们有多少种方法可以找零?硬币的顺序无关紧要。不过还有一个额外的限制:你只能用恰好 K 个硬币来找零。
例如,对于 N = 4、k = 2 和 S = {1,2,3},有两种解:{2,2},{1,3}。所以输出应该是2。
解决方案:
int getways(int coins, int target, int total_coins, int *denomination, int size, int idx)
{
int sum = 0, i;
if (coins > target || total_coins < 0)
return 0;
if (target == coins && total_coins == 0)
return 1;
if (target == coins && total_coins < 0)
return 0;
for (i=idx;i<size;i++) {
sum += getways(coins+denomination[i], target, total_coins-1, denomination, size, i);
}
return sum;
}
int main()
{
int target = 49;
int total_coins = 15;
int denomination[] = {1, 2, 3, 4, 5};
int size = sizeof(denomination)/sizeof(denomination[0]);
printf("%d\n", getways(0, target, total_coins, denomination, size, 0));
}
以上是递归解决方案。但是我需要动态编程解决方案的帮助:
让dp[i][j][k] 代表i 与j 元素和k 硬币的总和。
所以,
dp[i][j][k] = dp[i][j-1][k] + dp[i-a[j]][j][k-1]
我的循环关系对吗?
【问题讨论】:
-
应该和普通的硬币找零问题一模一样,但是剩下的硬币数量是一位数。我很惊讶你有一个 3D dp 矩阵。普通的硬币链通常是一维的,如果有一个额外的硬币,你应该最终得到一个二维矩阵。我想我想问的是 "j elements" 是什么意思?
-
@aioobe: j 是数组的索引。
-
是的,但它代表什么。
k代表硬币数量,j代表什么? -
@aioobe: algorithmist.com/index.php/Coin_Change 看看这个。
-
对。但仅仅因为你有 3 个嵌套循环并不一定意味着你需要一个 3D dp。
标签: dynamic-programming recurrence