0

The former seems to be much more "hip" in JavaScript, and I don't understand why.

Edit: in response to this question possibly being a duplicate, my interest is why, not how. And another question asking only about "closures" in the title wouldn't catch the eye of the person who hasn't made the link between this and closures yet.

Jim Smith
  • 151
  • 4
  • 17
  • possible duplicate of [How do JavaScript closures work?](http://stackoverflow.com/questions/111102/how-do-javascript-closures-work) – Filburt May 03 '15 at 15:29

1 Answers1

2

tl;dr: Because many functions are actually not reused.


I think you answered your own question:

... instead of just the function name which can be reused?

Many of these are "one-off" cases. The line of code is executed once and the passed function doesn't have to be reused.

For example, if I want to bind an event handler to a body and I don't intend to reuse the event handler anywhere, why should I write

function bodyEventHandler() {}
document.body.addEventListener('click', bodyEventHandler);

and unnecessarily pollute the current scope with bodyEventHandler?

document.body.addEventListener('click', function() {...});

has the same effect, doesn't pollute the scope and keeps the function definition where it is used.

JavaScript is very much event-driven, and most event handlers are actually not going to be reused anywhere else.


Keeping the function definition where the function is used is also a common reason IMO. Some functions are either very simple, but it may not be easy to give them descriptive names.

E.g. if you are not familiar with the term "pluck", would you understand what

var names = users.map(pluck('name'));

really does? Maybe you can infer it from the other variables names.

However,

var names = users.map(function(user) { return user.name; });

makes it immediately clear.

In fact, you will see these even more often, now that ECMAScript 6 introduces arrow functions, which are like lambda functions in other languages:

var names = users.map(user => user.name);

I also think you have a misconception of what exactly happens under the hood when you pass a function:

... pass an entire function definition as an argument instead of just the function name ...

foo(bar) does not pass the name "bar" to foo. It passes the function object that is referenced by the variable bar. That is no different from foo(function() { ... }). The only difference is that we are not (temporarily) storing the function in a variable.

Felix Kling
  • 705,106
  • 160
  • 1,004
  • 1,072
  • good explanation, bad example: working with event handling properly means that quite often you'll also need to call a `removeEventListener` later on, to prevent memory leaks, which means you'll need keep a reference to the function handler somewhere. Map/foreach etc are better examples. – Mike 'Pomax' Kamermans May 03 '15 at 16:08
  • @Mike'Pomax'Kamermans - there is no need to call `removeEventListener()` to prevent memory leaks. The fact that a DOM element has an eventListener does not prevent it from being garbage collected. The GC is smart enough to recognize that case when the DOM element is otherwise not reachable. – jfriend00 May 03 '15 at 16:11
  • For today's browsers that is often true, but there are more situations than just "when a DOM node is removed from the DOM" where eventlistening was bound and need to be cleaned up. The explosion in popularity of React apps immediately comes to mind. – Mike 'Pomax' Kamermans May 03 '15 at 16:18
  • Thanks Felix. Sometimes confirmation is just as important as learning new information. Simply saying that "many functions are actually not reused" could be considered sacrilegious to many programmers. So it helps to hear it. – Jim Smith May 03 '15 at 16:49