Maria
Maria

Reputation: 3525

javascript: modify global variable from local variable

I don't understand why in the function change2, the console doesn't output 2, but undefined?

var users = {a:1, b:2};

function change1(people){
    people.c = {};
    var C = people.c;
    setTimeout(function(){        
        C.number = 2;
    }, 1000);
}

function change2(people){
    people.c = {};
    var C = people.c;
    setTimeout(function(){
        console.log(C.number);
    }, 2000);
}

change1(users);
change2(users); // undefined, why not 2?

However, if I replace C.number by people.c.number within setTimeout of change1, it works(outputs 2), why? Don't they refer the same thing?

Upvotes: 1

Views: 319

Answers (2)

albanx
albanx

Reputation: 6335

This is my explanation. In the change1 this creates a new object, lets call it object1, and keeps a reference in the local variable C:

  people.c = {};
  var C = people.c;

In change2 let change the name of C in B (for avoiding confusion)

people.c = {};
var B = people.c;

This creates another new object, lets call it object2, that overrides the reference in people.c (so people.c points to this new object) and stores a reference to the local variable B.

So the local variable C in change1 points to object1, the local variable B points to object2 and people.c points to object2.

C.number = 2

will define the number property of object1 in change1

meanwhile

console.log(B.number) //console.log(C.number) in the original code

will try to output the property of object2 that is undefined.

Basically C in change1 and C in change2 are pointing to two different objects. setTimeout does not have any effect in this.

Upvotes: 1

andrew_m
andrew_m

Reputation: 121

Your change1 function assigns a new object to people.c and also stores it in local C variable. Then in change2 you create another new object and store is in people.c. So people.c (or rather users.c) holds now that second object.

After 1 second your change1 function creates a "number" property in the first object. But people.c already holds a second object which stays not modified. So after another 1 second change2 tries to find "number" property in the second object which do not have such property.

So in short you should remove

people.c = {};

from change2 so avoid overriding the people.c property.

Upvotes: 3

Related Questions