algorithm to sum up a list of numbers for all combinations

前端 未结 15 2258
北荒
北荒 2020-12-04 22:34

I have a list of numbers and I want to add up all the different combinations. For example:

  • number as 1,4,7 and 13
  • the output would be:

相关标签:
15条回答
  • 2020-12-04 23:29

    Here is a simple recursive Ruby implementation:

    a = [1, 4, 7, 13]
    
    def add(current, ary, idx, sum)
        (idx...ary.length).each do |i|
            add(current + [ary[i]], ary, i+1, sum + ary[i])
        end
        puts "#{current.join('+')} = #{sum}" if current.size > 1
    end    
    add([], a, 0, 0)
    

    Which prints

    1+4+7+13 = 25
    1+4+7 = 12
    1+4+13 = 18
    1+4 = 5
    1+7+13 = 21
    1+7 = 8
    1+13 = 14
    4+7+13 = 24
    4+7 = 11
    4+13 = 17
    7+13 = 20
    

    If you do not need to print the array at each step, the code can be made even simpler and much faster because no additional arrays are created:

    def add(ary, idx, sum)
        (idx...ary.length).each do |i|
            add(ary, i+1, sum + ary[i])
        end
        puts sum
    end
    add(a, 0, 0)
    

    I dont think you can have it much simpler than that.

    0 讨论(0)
  • 2020-12-04 23:33

    You might be interested in checking out the GNU Scientific Library if you want to avoid maintenance costs. The actual process of summing longer sequences will become very expensive (more-so than generating a single permutation on a step basis), most architectures have SIMD/vector instructions that can provide rather impressive speed-up (I would provide examples of such implementations but I cannot post URLs yet).

    0 讨论(0)
  • 2020-12-04 23:33

    Thanks Zach,

    I am creating a Bank Reconciliation solution. I dropped your code into jsbin.com to do some quick testing and produced this in Javascript:

    function f(numbers,ids, index,  sum, output, outputid, find )
    {
        if (index == numbers.length){
              var x ="";
              if (find == sum) {
                  y= output + " } = " + sum + "  " + outputid + " }<br/>" ;
              }
            return;
        }
        f(numbers,ids, index + 1, sum + numbers[index], output + " " + numbers[index], outputid + " " + ids[index], find);
        f(numbers,ids, index + 1, sum, output, outputid,find);
    }
    
    var y;
    
    f( [1.2,4,7,13,45,325,23,245,78,432,1,2,6],[1,2,3,4,5,6,7,8,9,10,11,12,13], 0, 0, '{','{', 24.2);
    if (document.getElementById('hello')) {
      document.getElementById('hello').innerHTML = y;
    }
    

    I need it to produce a list of ID's to exclude from the next matching number.

    I will post back my final solution using vb.net

    0 讨论(0)
提交回复
热议问题