C#货币兑换算法

时间:2016-12-09 09:34:30

标签: c#

我需要确定所有可能的钞票组合的给定输入。

int[] currency = new int[] { 5, 10, 20, 50, 100, 200, 500 };
int total = 20; // result is { {5,5,5,5} {5,5,10} {10,10} {20} }

int[][] result = GetCombinations(total, 0, currency); // should return the 4 combinations

这是我到目前为止所尝试的内容。

public static int GetCombinations(int total, int index, int[] list)
{   
    total = total - list[index];
    if (total < 0)
    {
        return 0;
    }
    else if (total == 0)
    {
        return 1;
    }
    else
    {
        return 1 + GetCombinations(total, index + 1, list);
    }
}

赏金问题:

我需要一种方法来获得所有组合 - 而不仅仅是计数。

1 个答案:

答案 0 :(得分:3)

您只计算{5},{5,10}。
您正在计算&#34;如果成本&lt; = 20?&#34;,可以使用多少个不同的硬币。
所以,你必须指望这个算法。
正确的代码是:

public static int GetCombinations(int total, int index, int[] list)
{  
    if (total == 0)
    {
        return 1;
    }
    if(index == list.Length) {
        return 0;
    }
    int ret = 0;
    for(; total >= 0; total -= list[index])
    {
        ret += GetCombinations(total, index + 1, list);
    }
    return ret;
}


如果要计算组合数,还可以解决dp[total][index]的动态编程和记忆,因为如果total和index相同,则GetCombinations(total, index, list)值相同。

编辑:
如果你想要所有组合,你可以这样做:

using System;
using System.Collections.Generic;
class Program {
    public static int GetCombinations(int total, int index, int[] list, List<int> cur) {  
        if (total == 0) {
            foreach(var i in cur) {
                Console.Write(i + " ");
            }
            Console.WriteLine();
            return 1;
        }
        if(index == list.Length) {
            return 0;
        }
        int ret = 0;
        for(; total >= 0; total -= list[index]) {
            ret += GetCombinations(total, index + 1, list, cur);
            cur.Add(list[index]);
        }
        for(int i = 0; i < cur.Count; i++) {
            while(cur.Count > i && cur[i] == list[index]) {
                cur.RemoveAt(i);
            }
        }
        return ret;
    }
    public static void Main() {
        int[] l = { 5, 10, 20, 50, 100, 200, 500 };
        GetCombinations(20, 0, l, new List<int>());
    }
}

我改进了代码,现在您可以使用递归来枚举所有组合 在此代码中,它按字典顺序列举组合 我核实了sum=20, 75个案例。