Javascript module structure and closure
I am trying to get my head around the module pattern in Javascript and came across various ways I can see to do this. What is the difference (if any) between the following:
Person = function() {
return {
//...
}
};
person1 = Person();
function Person2() {
return {
//...
}
}
person2 = Person2();
person3 = function() {
return {
//...
}
}();
person4 = (function() {
return {
// ...
}
})();
person5 = (function() {
return {
// ...
}
}());
They all seem to be doing the same to me.
source to share
// This creates a function, which then returns an object.
// Person1 isn't available until the assignment block runs.
Person = function() {
return {
//...
}
};
person1 = Person();
// Same thing, different way of phrasing it.
// There are sometimes advantages of the
// two methods, but in this context they are the same.
// Person2 is available at compile time.
function Person2() {
return {
//...
}
}
person2 = Person2();
// This is identical to 'person4'
// In *this* context, the parens aren't needed
// but serve as a tool for whoever reads the code.
// (In other contexts you do need them.)
person3 = function() {
return {
//...
}
}();
// This is a short cut to create a function and then execute it,
// removing the need for a temporary variable.
// This is called the IIFE (Immediate Invoked Function Expression)
person4 = (function() {
return {
// ...
}
})();
// Exactly the same as Person3 and Person4 -- Explained below.
person5 = (function() {
return {
// ...
}
}());
In the context above,
- = function () {} ();
- = (function () {} ());
- = (function () {}) ();
Everyone is doing the same.
I will break them.
function() {}();
<functionExpression>(); // Call a function expression.
(<functionExpression>()); // Wrapping it up in extra parens means nothing.
// Nothing more than saying (((1))) + (((2)))
(<functionExpression>)();
// We already know the extra parens means nothing, so remove them and you get
<functionExpression>(); // Which is the same as case1
Now all that said is why do you need partners sometimes?
Because this is a function statement *)
function test() {};
To make a function expression, it needs some kind of operator before it.
(function test() {})
!function test() {}
+function test() {}
everyone works.
By standardizing on parens, we can:
- Returns the value from the IIFE
- Use a consistent way so that the reader of the code knows that this is an IIFE and not a regular function.
source to share
The first two are not a module pattern, but a factory function - there is a Person
" constructor " that can be called multiple times. For the semantic difference see var functionName = function () {} vs function functionName () {} .
The other three are IIFEs , which all do exactly the same. For syntax differences, see Explaining the Syntax of Encapsulated Anonymous Functions and Bracket Location for Automatic Execution of Anonymous JavaScript Functions? ...
source to share