1
function myFunction() {
   function myInternalFunction() {
      return 10;
   }
   return myInternalFunction();
   function myInternalFunction() {
      return 20;
   }
}
alert(myFunction()); // What will this alert?

The answer is 20.

function myFunction() {
   var myInternalFunction = function() {
      return "Hello World.";
   }
   return myInternalFunction();
   var myInternalFunction = function() {
      return "Second Definition.";
   }
}
alert(myFunction()); // What will this alert?

The answer is "Hello Wold".

Why???? why not "Second Definition" ????

Bhojendra Rauniyar
  • 83,432
  • 35
  • 168
  • 231
  • 1
    See [var functionName = function() {} vs function functionName() {}](http://stackoverflow.com/q/336859/218196) – Felix Kling Apr 16 '14 at 03:19
  • Why? Because in the first example you are using function **declarations** and in the second one you are using function **expressions**. – Felix Kling Apr 16 '14 at 03:20
  • 1
    Regarding your edit, that's not equivalent to your previous example. You are calling `alert(a)` *after* the second assignment, so of course it alerts `two`. To make it equivalent to the function example, you would have to write `var a = 'one'; alert(a)', var a = 'two';`. – Felix Kling Apr 16 '14 at 03:29
  • @FelixKling oh! thank you..... and now completely removed my confusion. – Bhojendra Rauniyar Apr 16 '14 at 03:52

3 Answers3

3

Because, in the first case, during the compile time itself, second myInternalFunction replaces the first myInternalFunction in the current scope. It means that, only the second myInternalFunction function exists in the myFunction's scope.

But in the second case, the functions are created during the execution only. By the time alert was executed, only the first myInternalFunction function was created, the second myInternalFunction is not created at all. That is why Hello World is alerted.

thefourtheye
  • 233,700
  • 52
  • 457
  • 497
  • 1
    sorry, couldn't understand properly. – Bhojendra Rauniyar Apr 16 '14 at 03:19
  • The second case uses variabel declaration. This means it will be created once that code is executed .. but you never execute that piece of code sense you have a return statement before that. In the first case you simply state what functions existes in that scope. – superhero Apr 16 '14 at 03:43
3

A variable’s declaration is hoisted, but not its definition. So your second example is equivalent to:

function myFunction() {
   var myInternalFunction
   myInternalFunction = function() {
     return "Hello World."
   }
   return myInternalFunction()

   myInternalFunction = function() {
     return "Second Definition."
   }
}

Here it becomes obvious that the myInternalFunction is unreachable, so the first definition is used as it is the value of myInternalFunction at the time it’s called. JSLint correctly complains (using your original code):

Unreachable var after return.


Compare with your first example, where the function declarations are hoisted, so your code is equivalent to:

function myFunction() {
   function myInternalFunction() {
     return 10
   }
   function myInternalFunction() {
     return 20
   }
   return myInternalFunction()
}

As we can see here, myInternalFunction is immediately redeclared, and so the last one wins. Both declarations happen before calling the function itself.


So, why this expressions alert lastly called variable:

var a = "one";
var a = "two";
alert(a); // alerts two ???? shouldn't be "one" if expressions?

This isn’t equivalent to your function example; an equivalent example would be:

var a = "one"
alert(a)
var a = "two"

And expected it to alert “two”. I think it’s obvious it won’t. The value of the variable, be it function, string, or anything else, is not relevant.

Andrew Marshall
  • 95,083
  • 20
  • 220
  • 214
0

Function declarations and variable declarations are always moved (“hoisted”) invisibly to the top of their containing scope by the JavaScript interpreter.

Note it has to be Function declarations, which means only the syntax of function foo() {} will be hoisted.

First code is equal to:

function myFunction() {
   function myInternalFunction() {
      return 10;
   }
   function myInternalFunction() {
      return 20;
   }
   return myInternalFunction();
}

Second code is equal to:

function myFunction() {
   var myInternalFunction;

   myInternalFunction = function() {
      return "Hello World.";
   }

   return myInternalFunction();

   myInternalFunction = function() {
      return "Second Definition.";
   }
}
xdazz
  • 158,678
  • 38
  • 247
  • 274