Reputation: 21842
One of my friends was taking an online quiz and he asked me this question which I could not answer.
var global = false;
function test() {
global = true;
return false;
function global() {}
}
console.log(global); // says false (As expected)
test();
console.log(global); // says false (Unexpected: should be true)
If we assume that functions are hoisted at the top along with var variables, let's try this one.
var foo = 1;
function bar() {
return foo;
foo = 10;
function foo() {}
var foo = 11;
}
bar();
console.log(foo); //says 1 (But should be 11) Why 1 this time ??
Here is a JSBin Demo and JSBIN Demo2 to play with.
PS: If we remove function global() {}
from test()
, then it runs fine. Can somebody help me understand why is this happening ?
Upvotes: 7
Views: 243
Reputation: 665465
I'll answer the second part of your question,
If we assume that functions are hoisted at the top along with var variables
bar(); console.log(foo); //says 1 (But should be 11) Why 1 this time ??
You should try console.log(bar()); console.log(foo);
instead. However, what hoisting does to your function is this:
function bar() {
var foo;
function foo() {}
return foo;
foo = 10;
foo = 11;
}
So you should expect to get the function returned, since your variable assignments are after the return
statement. And both the var
and the function declaration make foo
a local variable, so the global foo = 1
is never changed.
Upvotes: 2
Reputation: 888185
var
statements and function declaration statements are "hoisted" to the top of their enclosing scope.
Therefore, the function global(){}
in your function creates a local global
name.
Assigning to global
inside your functions binds to this local name. Here's how you can "rewrite" it using hoisting to understand how the compiler sees it:
function test() {
var global = function() {}; // hoisted; 'global' now local
global = true;
return false;
}
Upvotes: 8