Domanda

I was trying to understand lexical scoping in Javascript. In the below example, I have written a function inside an another function. When I run this, I would expect to pop-up "dad" in the first alert and "mom" in the second alert. But what actually happens is, it shows "undefined" in the first pop-up and "mom" in the second.

function first(){
  var x = "dad"; 
  function second(){
    alert(x);
    var x = "mom";
    alert(x);
  }
  second();
}
first();

Can someone please explain why variable "x" defined in parent function is not visible in the child function? Strangely, when I remove the declaration for variable "x" inside the child function, it works fine. Could someone give insight of the lexical scoping scenario valid here?

È stato utile?

Soluzione 2

You re-declared x in second by using a var statement after the alert. This makes it a different x than the one declared in first.

Furthermore, JavaScript uses a technique called hoisting. When a variable is declared in a scope, that declaration is moved to the top of the scope during a pre-execution pass. If declaration and assignment are being done in one statement, the declaration is broken away from the assigment. Declaration is moved to the top of the scope, causing an undefined variable, while assigment is left where it origianally was.

The resulting code after the pre-pass is something like below (I've only showed hoisting of variables here and left functions alone)

function first(){
    var x;
    x = "dad";
    function second(){
        var x; //new variable in local scope, declared not defined
        alert(x); //alerts undefined
        x = "mom"; //defines local `x` as "mom"
        alert(x); //alerts "mom"
    }
    second();
}
first();

Thus, in the first alert your x is new and undefined, and in the second it is defined. Meanwhile, the value of x in first has remained unchanged.

In order to get what you were expecting, and to keep the same x in both functions, you would remove the var declaration from second and leave the assignment:

function first(){
    var x = "dad"; 
    function second(){
        alert(x);
        x = "mom";
        alert(x);
    }
    second();
}
first();

Altri suggerimenti

The var x in 'second' declares a variable 'x', which hides the variable 'x' in the outer function. Any reference to 'x' in 'second' function refers to that variable, even if it's before the declaration. The value of the variable before the declaration will be 'undefined'.

You can look up 'hoisting' for more information. See: http://www.adequatelygood.com/JavaScript-Scoping-and-Hoisting.html

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top