Filling array until sum of array equals X value

Hi! This should be easy but I'm stuck :-/

I have the values 3,4 and 5

I have an array where I put these values randomly. The array stops accepting values when the total sum of values hits 50. I'm close, but sometimes the total sum is 48 or 49 because in some cases the partial sum is 48 or 49 and my lowest value is 3 to fill it. I need that (whatever the distribution of values is) the sum is always 50.

How to do this in an elegant way?

Tagged:

Answers

  • Well with an if check if you're at 48/49

    If so, insert the last value as a new value lastValue=50-sumUpToNow;

    So lastValue is 1 or 2 if that's ok.

    Alternativly, when you add a last value 3/4/5 you end up with a val >50 - let's call it surplus

    Now say

    surplus = sumUpToNow-50;

    This should give 1 or 2

    Now for loop over the array or randomly pick a 5 and substract surplus from it

    So you modify an old entry to make the entire sum be 50

  • When you calculate the next random number (3, 4 or 5) only add it to the array IF it makes the new sum <= 47 OR == 50 in other words there will either be room for another number or you have reached your target.

  • Yeah, I thought of that at first but I can't find the optimal solution (in this case the sum of the array varies, even checking for surplus..

    int[] slot = new int[23]
    
    void setup(){
     slot = new int[23];
      int n=0;
      int val;
    
        do {
    
          if (int(random(1,10))==2) { val=5; } 
            else { val=round(random(3,4)); }
    
            slot[n]=val;       
            //println(n,":",val,int(arrSum(slot)));        
            n++;         
          } while (arrSum(slot)<=47);
    
         int diff=int(arrSum(slot))-50;
    
         if (diff>0) {
          for(int c=0;c<=slot.length-1;c++){
            if (slot[c]==5){
              slot[c]=slot[c]-diff;
            }
          } 
         }else {
            for(int c=0;c<=slot.length-1;c++){
            if (slot[c]==3){
              slot[c]=slot[c]+abs(diff);
            }
          }        
         }
    
      println(diff,int(arrSum(slot)));
    }
    
    
    float arrSum(int[] arr){
     float sum = 0;
     for (int i =0; i<arr.length; i++) {
          sum +=arr[i];
       }
     return sum;
     }
    
  • Note that an elegant solution would not use a for loop to populate the array rather it would use a while loop and a do-while loop. ;)

  • Please enlighten me (the 'elegant' part was referring to something that didn't use some long and painstaking manual check). I know this is a mess, just trying to find something that works first, then I'll do some cleaning. (we'll see about that, all my code tends to look like a geological dump of patches and duct tape).

  • edited October 2016 Answer ✓

    The for-loop is useful if you know the number of times the loop-body-code is to be executed. This is not the case because although you know you want the sum to equal 50 you don't know how many numbers will end up in the array.

    In the code below sum50 method populates the array with the numbers 3, 4 or 5 until the total is 50. It does not use a for-loop.

    void setup() {
      int[] array = new int[20];
      for (int i = 0; i < 10; i++) {
        clearArray(array);
        sum50(array);
        showArray(array);
      }
    }
    
    void clearArray(int[] a) {
      for (int i = 0; i < a.length; i++)
        a[i] = 0;
    }
    
    void sum50(int[] a) {
      int sum = 0, nextSum = 0, idx = 0, rn;
      while (sum != 50) {
        do {
          rn = int(random(3, 6)); // 3, 4 or 5
          nextSum = sum + rn;
        } while (!(nextSum <= 47 || nextSum ==  50));
        sum = nextSum;
        a[idx++] = rn;
      }
    }
    
    void showArray(int[] a) {
      int sum = 0, i = 0;
      print("[ ");
      while (a[i] != 0) {
        print(a[i] + " ");
        sum += a[i];
        i++;
      }
      println("]  Sum = " + sum);
    }
    

    A sample run output

    [ 5 3 5 4 5 4 5 5 3 4 4 3 ]  Sum = 50
    [ 5 4 5 3 3 5 4 4 3 3 3 3 5 ]  Sum = 50
    [ 3 3 4 3 4 5 3 3 5 4 3 5 5 ]  Sum = 50
    [ 5 4 5 5 3 5 5 4 3 5 3 3 ]  Sum = 50
    [ 4 4 5 3 5 3 3 3 3 4 3 4 3 3 ]  Sum = 50
    [ 5 5 4 4 3 3 5 3 4 3 3 3 5 ]  Sum = 50
    [ 4 3 5 4 4 3 5 5 4 4 3 3 3 ]  Sum = 50
    [ 5 4 4 4 5 5 5 3 4 5 3 3 ]  Sum = 50
    [ 4 5 3 4 4 3 5 5 4 4 3 3 3 ]  Sum = 50
    [ 5 3 4 3 5 5 3 3 3 4 4 3 5 ]  Sum = 50
    
  • Thanks @quark ,really helpful

Sign In or Register to comment.