user2846577
user2846577

Reputation: 43

Finding the sum of a nested array

I tried finding the sum of all numbers of a nested array, but I don't get it to work correctly. This is what I tried:

function arraySum(i) {
  sum = 0;
  for (a = 0; a < i.length; a++) {
    if (typeof i[a] == 'number') {
      sum += i[a];
    } else if (i[a] instanceof Array) {
      sum += arraySum(i[a]);
    }
  }
  return sum;
}

When you try it out with the array [[1,2,3],4,5], it gets 6 as the answer, instead of 15. Does somebody know where there is a mistake in it?

Upvotes: 4

Views: 18470

Answers (10)

Iglesfe
Iglesfe

Reputation: 1

This was posted long ago but it might help others. I did the following and it seems to be working just fine

function countArray (array) {
 //iterate through the array
for(let i = 0;i < array.length; i++){
//check if element of array is an array, and if it is, run method flat() to the whole array. 
  if(Array.isArray(array[i])){
    array = array.flat()
  }
}
//return the sum of the elements of the array
 return array.reduce((a,b) => a + b);
    
}

Upvotes: 0

Santiago M. Quintero
Santiago M. Quintero

Reputation: 1273

For 2018 this solution is clean and functional:

let arr = [[ 1, 2, 3], 4, 5]
arr.flat().reduce((d, i) => d + i)

Documentation for flat and reduce.

Upvotes: 3

WesleyAC
WesleyAC

Reputation: 553

Here you go:

(My assumption is that you want to parse strings, e.g., '13', into numbers in order include them in the sum. If not, just change isNumber to typeof val === 'number'.

function arraySum(arr) {
  let sum = 0;

  while (arr.length) {
    const val = arr.pop();
    const isArray = typeof val === 'object' && val.length !== undefined;
    const isNumber = !isArray && !isNaN(sum + parseFloat(val)); 

    if (isArray && val.length) {
      sum += arraySum(val);
    }
    else if (isNumber) {
      sum += parseFloat(val);
    }
  }

  return sum;
}

console.log(arraySum([])); //0
console.log(arraySum([1, 1, 1, [3, 4, [8]], [4]])); //22
console.log(arraySum([1, 1, [], {}, 'l', 1, [3, 4, [8]], [4]])); //22

Upvotes: 1

Th1
Th1

Reputation: 291

I know it's late, but they say "is never late" :)

const sumNestedArray = arr => arr.flat(Infinity).reduce((a,b)=> a+b, 0)

const sumNestedArray = arr => arr.flat(Infinity).reduce((a,b)=> a+b, 0)

console.log(sumNestedArray([1,[2], [2, 3, [4]]]))

sumNestedArray([1,[2], [2, 3, [4]]])

Upvotes: 5

Penny Liu
Penny Liu

Reputation: 17408

This can be done with lodash _.flattenDeep and _.sum:

const arr = [[1, 2, 3], 4, 5];
arraySum(arr);

function arraySum(arr) {
  var arrFlattens = _.flattenDeep(arr);
  // => [1, 2, 3, 4, 5]
  console.log(_.sum(arrFlattens));
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.11/lodash.min.js"></script>

Upvotes: 0

mohan kumar
mohan kumar

Reputation: 19

from __builtin__ import int
def nestedLists(mylist):
    sum = 0
    if checkIfAllInt(mylist):
        result = addList(mylist)
        return result
    else:
        for value in mylist:
            sum = sum + nestedLists(value)
    return sum        

def addList(listdata):
    if(type(listdata) is int):
        return listdata
    else:
        return sum(listdata)    

def checkIfAllInt(listdata):
    check = True
    if(type(listdata) is int):
        return check
    else:
        for value in listdata:
            if(not type(value) is int):
                check = False
                return check
    return check    

print nestedLists([1,[2,3,[4,5,[6,7]]]])    

Upvotes: -1

Mendi Barel
Mendi Barel

Reputation: 3677

First of all why you use 'i' as input to function? we using 'i' to denote running index.. Regarding your question,you want 'a' to be local in your loop so instead of "for(a=0;..." instead write "for(var a=0;"

    <html>
    <body>
        <script>
            function NestedArraySummation(arr)
            {
                var sum=0;
                for(var i=0;i<arr.length;i++)
                {
                    if(typeof arr[i]=="number")
                    sum=sum+arr[i];
                    else  if(arr[i] instanceof Array)
                        sum=sum+NestedArraySummation(arr[i]);
                }
                    return sum;
            }

            var MyArray=[1,[2,3],4,10,[1,2]];
            var Sum=NestedArraySummation(MyArray);
            document.write(Sum);

        </script>
    </body>
</html>

Upvotes: 0

Tibos
Tibos

Reputation: 27823

The problem with your code is that the sum and a variables are global, instead of local. Because of this you get an infinite loop (a from the first entry in the function is reset by the second entry, so the same elements are processed again).

Fix it by adding var to where sum and a are declared to make them local to the function:

function arraySum(i) {
    var sum=0; // missing var added
    for(var a=0;a<i.length;a++){ // missing var added
        if(typeof i[a]=="number"){
            sum+=i[a];
        }else if(i[a] instanceof Array){
            sum+=arraySum(i[a]);
        }
    }
    return sum;
}

Demo: http://jsbin.com/eGaFOLA/2/edit

Upvotes: 9

CodingIntrigue
CodingIntrigue

Reputation: 78525

You're missing two var in there. You've implicitly declared sum and a at window scope:

function arraySum(i) {
    **var** sum=0;
    for(**var** a=0;a<i.length;a++){
        if(typeof i[a]=="number"){
            sum+=i[a];
        }else if(i[a] instanceof Array){
            sum+=arraySum(i[a]);
        }
    }
    return sum;
}

Upvotes: 0

Paul S.
Paul S.

Reputation: 66304

Recurse, for example

function arraySum(x) {
    var sum = 0, i;
    if (typeof x === 'number')
        return x;
    else if (x instanceof Array)
        for (i = 0; i < x.length; ++i)
            sum += arraySum(x[i]);
    return sum;
}
arraySum([[1,2,3],4,5]); // 15

I didn't optimise this so that it's clear, you may want some more logic before recursion.


The reason yours isn't working is because you need to var both sum and a.

Upvotes: 0

Related Questions