1

Could you please tell me why this code isn't working properly?

The flatten function suppose to remove values from any arrays inside the input array and return those values as a array.

function flatten(arr) {
  //create a new array
  let newArr = [];

  //create a helperFunction
  function helperFunction(helperArr) {
    //if its an empty array
    if (helperArr.length === 0) {
      return;
    }

    //get the first value from the array and remove the value
    let firstArrVal = helperArr.shift();
    let isAnArray = Array.isArray(firstArrVal);

    //if value is an array 
    if (isAnArray) {
      //call recursive function on value
      return helperFunction(firstArrVal);
    }
    //if value isnt an array
    else {
      //add value to new array
      newArr.push(firstArrVal);
      //call recursive function on the array
      return helperFunction(helperArr);
    }
  }

  //call helperFunction
  helperFunction(arr);

  //return new array
  return newArr;
}

console.log(flatten([1, [2, [3, 4],
  [
    [5]
  ]
]]));

// Correct output - [1, 2, 3, 4, 5] - Mine - [1, 2, 3, 4]

For input [1, [2, [3, 4], [[5]]]] the correct output is [1, 2, 3, 4, 5] (mine - [1, 2, 3, 4])

Kamil Kiełczewski
  • 85,173
  • 29
  • 368
  • 345

2 Answers2

1

You need to iterate through all elements of a subarray, and either push them or call helperFunction on them. Your current

    let firstArrVal = helperArr.shift();
    let isAnArray = Array.isArray(firstArrVal);

will only merge the first nested values, but not any nested indicies past the 0th. Use a for loop instead, for every value in the array:

function flatten(arr) {
  //create a new array
  let newArr = [];

  //create a helperFunction
  function helperFunction(helperArr) {
    //if its an empty array
    if (helperArr.length === 0) {
      return;
    }
    for (let i = 0; i < helperArr.length; i++) {
      const val = helperArr[i];
      let isAnArray = Array.isArray(val);

      //if value is an array 
      if (isAnArray) {
        //call recursive function on value
        helperFunction(val);
      }
      //if value isnt an array
      else {
        //add value to new array
        newArr.push(val);
      }
    }
  }

  //call helperFunction
  helperFunction(arr);

  //return new array
  return newArr;
}

console.log(flatten([1, [2, [3, 4],
  [
    [5]
  ]
]]));

Or, to be more concise, use flat (add a polyfill for incompatible browsers):

const flatten = arr => arr.flat(Infinity);

console.log(flatten([1, [2, [3, 4],[[5]]]]));
CertainPerformance
  • 356,069
  • 52
  • 309
  • 320
  • Thanks for your quick response @CertainPerformance. I was trying to do this with out using any loops. I thought this could be done with out any loops. I guess with recursion we can only travel linear. Thanks again. – Dilan Livera Feb 07 '19 at 00:22
  • Unless every nested array will only ever contain one element, you'll have to use some sort of loop to loop through every element and check whether it's an array or plain value. – CertainPerformance Feb 07 '19 at 00:24
  • When an answer is helpful to you, you can consider marking it as Accepted to indicate that your issue is resolved :) – CertainPerformance Feb 07 '19 at 00:29
-1

The problem with your code is that you not iterate over (sub)arrays elements - as alternative you can use flatMap (and fat arrow) in following recursive function

let arr=[1, [2, [3, 4], [[5]]]];
let flatten = a => a.flatMap(x=> Array.isArray(x) ? flatten(x) : x);

console.log(flatten(arr));
Kamil Kiełczewski
  • 85,173
  • 29
  • 368
  • 345
  • Thanks for pointing out my mistake. I realize now its not possible to travel through multidimensional objects using recursion. Thanks for help. – Dilan Livera Feb 07 '19 at 00:34
  • @DilanWaduge I don't understand what do you mean by "multidimensional object" - however above `flatten` function is recursive (it call itself inside its body) and it travel through multidimensional array (so in case of array it is possible) – Kamil Kiełczewski Feb 07 '19 at 08:43
  • I was referring to objects inside objects. Like you said flatMap is only possible on JavaScript arrays. Thanks for pointing out flatMap. Its a useful method to know. – Dilan Livera Feb 08 '19 at 22:55
  • @DilanWaduge I think recursive travel in nested object is possible - look [here](https://stackoverflow.com/q/2549320/860099). – Kamil Kiełczewski Feb 09 '19 at 12:54
  • Thanks for the link. for in loop seems to do the trick. Thanks for your help. – Dilan Livera Feb 11 '19 at 00:39