skip to Main Content

I have 3 inputs: an array, a total count integer and an arbitrary value.

input_array = ['hello', 'there', 'world']
total_count = 15
fill_value = null

Desired output:

output = [
  'hello',
   null,
   null,
   null,
   null,
   'there',
   null,
   null,
   null,
   null,
   'world',
   null,
   null,
   null,
   null,
]

Assume that the length of input_array does not exceed total_count. Other scenarios:

  • If total_count was 3, you’d get ['hello', 'there', 'world']
  • If total_count was 4, you’d get ['hello', null, 'there', 'world']
  • etc. etc.

This feels like a candidate for a recursive function? You could take Math.ceil((total_count - input_array.length) / input_array.length) and use that value to fill in the slots but I’m not sure what the cleanest syntax would look like.

2

Answers


  1. You can use Array#flatMap to construct the final array.

    function createArr(initial, count, fill) {
      const each = Math.floor(count / initial.length) - 1, rem = count % initial.length;
      return initial.flatMap((x, i) => [x, ...Array(each + (i < rem)).fill(fill)]);
    }
    console.log(createArr(['hello', 'there', 'world'], 15, null));
    console.log(createArr(['hello', 'there', 'world'], 4, null));
    console.log(createArr(['hello', 'there', 'world'], 3, null));
    Login or Signup to reply.
  2. The trick is figuring out where the items go. If the number of elements does not fit the output array evenly, every index will be pushed right by one for each previous item to evenly distribute the overhead:

    function fillPadded(arr, count, fillWith){
      const filled = Array(count).fill(fillWith)
      const step = Math.floor(count/arr.length)
      const offs = count%arr.length
      for(let i = 0; i < arr.length; i++){
        const pos = i*step + (i <= offs ? i : offs) // or Math.min(i, offs)
        filled[pos] = arr[i]
      }
      return filled
    }
    
    console.log(JSON.stringify(fillPadded(['hello', 'there', 'world', 'foo'], 9, null)))
    console.log(JSON.stringify(fillPadded(['hello', 'there', 'world', 'foo'], 10, null)))
    console.log(JSON.stringify(fillPadded(['hello', 'there', 'world', 'foo'], 11, null)))
    console.log(JSON.stringify(fillPadded(['hello', 'there', 'world'], 15, null)))
    .as-console-wrapper { max-height: 100% !important; top: 0; }
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search