Why is this javascript snippet logging 1?

Viewed 103

In an interview, I was asked to guess the output of the following snippet:

var foo = 1;
    
function bar() {
    foo = 10;
    return;
    function foo() {
    }
}

bar();

console.log(foo);

and I thought the output will be 10 because the bar function returns right after reassigning the value of foo but the actual output is 1. Is it because of the function definition with the same variable name(foo)? Is a new scope created for the foo variable inside bar?

2 Answers

That's a nasty (and somewhat pointless) question to ask in an interview!

It is indeed got to do with the function foo in the scope of bar - without that it does what you would have expected.

 var foo = 1;
    
function bar() {
    foo = 10;
    return;
    
}

bar();

console.log(foo);

The reason is due to "hoisting" - the function declaration within bar gets hoisted to the start of the function bar as a new variable, and due to the nature of javascript letting you change the type at runtime, it allows you to set it (and not the global) foo to 10.

It is essentially the same as this code:

 var foo = 1;
    
function bar() {
    var foo;
    foo = 10;
}

bar();

console.log(foo);

The function declaration inside bar creates a new local name foo, which shadows the outer one. Essentially the function foo() {} line is hoisted to the top of the function. You can see this here:

function bar() {
    console.log(foo);
    foo = 10;
    console.log(foo);
    return;
    function foo() {}
}

bar();

So foo = 10 modifies the local foo name, not the global one.

Related