Search code examples
javascriptiife

Why value of `X` in iife chage based on the way we access it?


I have following js code.

var a = (function(){
    var x = 0;
    var y = function(){
        x++;
        console.log(x);
    }
    var z = function(){
        return x;
    }
    return {
        x, y, z
    }
})();

Here when I try to access a.x for the first time, It is giving me output 0(which is expected as x is initialized to 0), Then I am incrementing the value of x using function y. But after incrementing value of x two times(or maybe more then 2), when I try to access the value of x it is stll giving me a.x=0. I am not able to understand why it is happening as I already change the value of x using function y. Then why it is not changing.

(But when I am accessing value of x through some function it is giving incremented value. Why this different behavior. if the same variable I am directly access then it will give some output and when the same variable value I am returning through some function it is giving some other value. Why?)

var a = (function(){
  var x = 0;
  var y = function(){
	x++;
	console.log(x);
  }
  var z = function(){
	return x;
  }
  return {
	x, y, z
  }
})();

console.log(a.x);
a.y();
a.y();
console.log(a.x);
console.log(a.z());

I guess it is because of closure but not sure about it.


Solution

  • When you create an object and return it:

    return {
      x, y, z
    }
    

    The x property in the object receives a copy of the local variable x. It is not bound in any way to the local variable other than that, so subsequent changes to the variable in the closure are not reflected in that object.

    You could make a getter:

    return {
      get x() { return x; },
      y, z
    };
    

    That will cause any access to the "x" property of the returned object fetch the current value of x in the closure.