0

I've searched SO for this question and can't seem to find it: how does passing an argument in a called function directly to a nested function work? For example, take the following code, from "Eloquent Javascript:"

var dayName = function() {
  var names = ["Sunday", "Monday", "Tuesday", "Wednesday",
               "Thursday", "Friday", "Saturday"];
  return function(number) {
    return names[number];
  };
}();

console.log(dayName(3));
// → Wednesday

The argument 3 is passed to dayName(), but dayName() does not accept any parameters directly. How does the argument get passed to the nested returned function? How would this differ is the nested function wasn't returned itself, but instead returned a value?

Lastly, consider this pseudo-code, where two arguments are passed to the dayName() function, and both the dayName() function and its nested function accept params:

var dayName = function(param) {
  console.log(param);
  (function(otherParam) {
    console.log(otherParam);
  });
};

dayName(outerFunctionParam, innerFunctionParam);

What is the proper syntax to pass one param to the dayName() function and the second param to the nested function, and how does it work behind the scenes? Thanks!

Ivan Durst
  • 1,163
  • 2
  • 12
  • 24
  • Possible Duplicate of [Cannot Understand this JavaScript Construct](http://stackoverflow.com/questions/35797301/cannot-understand-this-javascript-construct) – Tushar Mar 08 '16 at 03:37
  • @Tushar: While that question and mine are both pointing to the same piece of code from that book, we're asking two very different questions about it. – Ivan Durst Mar 08 '16 at 03:39
  • 1
    The function assigned to `dayName` is IIFE which returns another function, `dayname` = _inner function_ + _outer function vars_. – Tushar Mar 08 '16 at 03:39
  • If you understand how the code works, your problem will be solved. :) – Tushar Mar 08 '16 at 03:40
  • @Tushar: Thanks, I'll spend some time on the other question and see if that solves my issue :) – Ivan Durst Mar 08 '16 at 03:44
  • FWIW, this article was also helpful: http://jtfmumm.com/blog/2013/08/31/nested-higher-order-functions-in-javascript/ – Ivan Durst Mar 08 '16 at 04:17

4 Answers4

1

The thing is parenthesis at the end of dayName assignment. When the dayName is assigned the parenthesis at the end, this the function returned is assigned to dayName, not the outer function itself.

var a = function ( ) { 
    return 1;
}

var b = a; // the function a is assigned to b
var b = a(); // the function is executed hence the value returned by a is stored in b. That is 1

Please take a look:

UPDATE

var dayName = function(param1, param2) {
  console.log('param 1: ' + param1);
  (function(otherParam) {
    console.log('param 2: '+otherParam);
  })(param2);
};

dayName(1); // 1, undefined
dayName(1,2); // 1,2
Ivan Durst
  • 1,163
  • 2
  • 12
  • 24
Pravin
  • 1,671
  • 5
  • 23
  • 36
  • I thought I understood IIFE's, but this was an 'aha' moment. The update is helpful too, thank you. Note that your update code wasn't working as written, so I corrected it :) – Ivan Durst Mar 08 '16 at 04:11
1

This is a a great question! It hinges on the fact that the dayName function is an Immediately Invoked Function Expression (IFFE)

Because of that its immediately called.

If you take of the (); at the end of the function, like so, it's going to work how you're thinking it should

var dayName = function() {
var names = ["Sunday", "Monday", "Tuesday", "Wednesday",
           "Thursday", "Friday", "Saturday"];
  return function(number) {
  return names[number];
  };
}(); // take that '()' out and this function will just return a function
     // with it on, it Immediately calls the function, returning 'Wednesday'

working JSBin: https://jsbin.com/zenajed/1/edit?js,console

omarjmh
  • 13,632
  • 6
  • 34
  • 42
1

If we rewrite the example without anonymous function, this will look like this:

var theAnonymousFunction = function() {
  var names = ["Sunday", "Monday", "Tuesday", "Wednesday",
               "Thursday", "Friday", "Saturday"];
  return function(number) {
    return names[number];
  };
}; // no () here

var dayName = theAnonymousFunction();// call the anonymouse function to get a function(number) as returned object

console.log(dayName(3));
wan rui
  • 36
  • 4
0

The dayName function is a closure with a private variable. You access that array var through

return names[number];

of the internal function. Number is passed into the names to declare which value in the array to grab.

In essence this is what is happening

var dayName = function(number) {
    return names[number];
  };

The names variable is private and can only be accessed by the function. So return names goes into the function and grabs that var for use.

Your code.

var dayName = function() {
  var names = ["Sunday", "Monday", "Tuesday", "Wednesday",
               "Thursday", "Friday", "Saturday"];
  return function(number) {
    return names[number];
  };
}();

SECOND QUESTION.…………

Your dayName function with multiple parameters will only use the first parameter because the second one was never declared in the function. You will get an undefined error.

var dayName = function(param, otherParamNeedsToBeDeFinedHere) {

Parameters are variable that are declared and used in functions. You can create as many as possible but you don't have to use them all in your code.

dayName(2);
// and
dayName(2,4);

Will both work if the function has at least two parameters.

Your code.

var dayName = function(param) {
  console.log(param);
  (function(otherParam) {
    console.log(otherParam);
  });
};

dayName(outerFunctionParam, innerFunctionParam);
andre mcgruder
  • 1,120
  • 1
  • 9
  • 12