Kevin
Kevin

Reputation: 19

javascript push method on global object array overwrites all values in array

I've reviewed previous posts on this problem, but have not been able to get the generally proposed solution to work for me. evtList is a global array of objects of type "Event". Previous posts have indicated that creating a local object ("newEvent") inside my loop, defining it's elements, and then pushing the local object into the global array should work. However, I've found that as soon as I declare a new value for an element in the newEvent object, all the objects in the global array are changed to that set of values even before the push operation. What have I missed?

var i = 0;
var nextTime = new Date();

while (evtList[i].evtTime < dayEnd) {
    i++;
    var newEvent = new Event;
    var milliSecs = (evtList[i-1].evtTime).getTime() + gaussian(arrStations[0].mean, arrStations[0].stdDev);
    nextTime.setTime(milliSecs);
    newEvent = ({value: 1, station: 0, evtTime: nextTime});

    evtList.push(newEvent);
}

Upvotes: 1

Views: 1498

Answers (1)

t.niese
t.niese

Reputation: 40842

In JavaScript var does not define a block level scope but a function level scope, so newEvent is not local to the your for loop, but to the the function body it belongs to, or to the global scope if it is not in a function.

With you push you add different objects to your evtList, but the problem is that the property evtTime of each of your objects reference the same Date object, so with nextTime.setTime(milliSecs) you will change the date for all of your evtTime properties, because it is the same object.

You would need to create a new Date object for each of you objects:

var newEvent;
var milliSecs;
var nextTime;
var i = 0;

while (evtList[i].evtTime < dayEnd) {
  i++;
  // newEvent = new Event;
  nextTime = new Date;
  milliSecs = (evtList[i - 1].evtTime).getTime() + gaussian(arrStations[0].mean, arrStations[0].stdDev);
  nextTime.setTime(milliSecs);
  newEvent = ({
    value: 1,
    station: 0,
    evtTime: nextTime
  });

  evtList.push(newEvent);
}

The newEvent you push to your evtList is not of the type Event, because the Event object that you have created with newEvent = new Event overwritten by a plain JavaScript object here:

newEvent = ({
  value: 1,
  station: 0,
  evtTime: nextTime
});

You either want to set just the properties of the newly created Event object:

newEvent.value = 1;
newEvent.station = 0;
newEvent.evtTime = nextTime;

Or you might pass them to your Event constructor.

Upvotes: 1

Related Questions