我目前正在尝试编写C#代码,它们在求和时找到多个等于指定总数的整数数组.我想找到这些组合,而数组中的每个整数都给出了它可以的范围.
例如,如果我们的总数是10并且我们有一个大小为3的int数组,其中第一个数字可以在1到4之间,第二个数字2和4,以及第三个3和6,一些可能的组合是[1,3, 6],[2,2,6]和[4,2,4].
什么样的算法有助于解决像这样的问题,可以在最有效的时间内运行?另外,在将此问题转换为C#代码时,我应该记住哪些其他事项?
最佳答案 我会使用递归来做到这一点.您可以简单地迭代所有可能的值,看看它们是否给出了所需的总和.
输入
假设我们有以下输入模式:
N S
min1 min2 min3 ... minN
max1 max2 max3 ... maxN
以你为榜样
if our total is 10 and we have an int array of size 3 where the first
number can be between 1 and 4, the second 2 and 4, and the third 3 and
6
这将是:
3 10
1 2 3
4 4 6
解
我们已经阅读了输入值.现在,我们只是尝试将每个可能的数字用于我们的解决方案.
我们将有一个List来存储当前路径:
static List<int> current = new List<int>();
递归函数非常简单:
private static void Do(int index, int currentSum)
{
if (index == length) // Termination
{
if (currentSum == sum) // If result is a required sum - just output it
Output();
return;
}
// try all possible solutions for current index
for (int i = minValues[index]; i <= maxValues[index]; i++)
{
current.Add(i);
Do(index + 1, currentSum + i); // pass new index and new sum
current.RemoveAt(current.Count() - 1);
}
}
对于非负值,我们也可以包括这样的条件.这是递归改进,它将切断大量不正确的迭代.如果我们已经有一个大于sum的currentSum,那么在这个递归分支中继续是没用的:
if (currentSum > sum) return;
实际上,这个算法是一个简单的“查找组合,给出和S”问题解决方案有一个区别:minValue [index]和maxValue [index]内的内循环索引.
演示
这是我的解决方案的工作IDEOne demo.