Sarah Gomez Sarah Gomez - 6 months ago 9
Javascript Question

Array push in for loop have different value in Object container

Im new to programming and just wondering why the output newContainer is different from what I have push inside the forloop. Check the console.log for details.

var data = [{
Fruit: "Apple",
Count: "1",
Date: "2014"
}, {
Fruit: "Banana",
Count: "1",
Date: "2015"
}, {
Fruit: "Carrot",
Count: "1",
Date: "2014"
}, {
Fruit: "Orange",
Count: "1",
Date: "2016"
}, {
Fruit: "Apple",
Count: "1",
Date: "2012"
}, {
Fruit: "Banana",
Count: "1",
Date: "2011"
}, {
Fruit: "Apple",
Count: "1",
Date: "2010"
}];



var lineItemCount = new Array(5).fill(0);
var lineItems = ["Apple", "Banana", "Carrot", "Orange"];
var newContainer = [];

for (var i = 0; i < data.length; i++) {

var checkItem = lineItems.indexOf(data[i].Fruit); //get index of item in lineItems

lineItemCount[checkItem] = lineItemCount[checkItem] + 1;
lineItemCount[0] = data[i].Date;

newContainer.push(lineItemCount);
console.log(lineItemCount);

};
console.log(newContainer);


Im trying to get the output like below. Thank you!

["2014", 1, 0, 0, 0],
["2015", 1, 1, 0, 0],
["2014", 1, 1, 1, 0],
["2016", 1, 1, 1, 1],
["2012", 2, 1, 1, 1],
["2011", 2, 2, 1, 1],
["2010", 3, 1, 1, 1],

Answer

The main issue is that you push the same array over and over again to the result. Although at the moment of the push, the array has different values than the next push, an array is a reference, and so when the values inside the array are incremented, any reference to that array will see this, even those references you already pushed.

Here is corrected code which uses slice(0) to copy array elements into a new array which then is pushed:

// 5 elements, first one for date
var lineItemCount = new Array(5).fill(0);

var lineItems = [null, "Apple", "Banana", "Carrot", "Orange"];
var newContainer = [];

for (var i = 0; i < data.length; i++) {

    var checkItem = lineItems.indexOf(data[i].Fruit); //get index of item in lineItems

    lineItemCount[checkItem] = lineItemCount[checkItem] + 1;
    lineItemCount[0] = data[i].Date;

    newContainer.push(lineItemCount.slice(0)); // take array copy
    console.log(lineItemCount);

};
console.log(newContainer);

Note also the additional item in the array with fruit names. This makes sure you don't increment element at index 0 which you have reserved for the dates.

Comments