Immediately invoked function expression explained

An immediately invoked function expression (or IIFE, pronounced "iffy", IPA /ˈɪf.i/) is a programming language idiom which produces a lexical scope using function scoping. It was popular in JavaScript[1] as a method to support modular programming before the introduction of more standardized solutions such as CommonJS and ES modules.[2]

Immediately invoked function expressions can be used to avoid variable hoisting from within blocks, protect against polluting the global environment and simultaneously allow public access to methods while retaining privacy for variables defined within the function.

Usage

Immediately invoked function expressions may be written in a number of different ways.[3] A common convention is to enclose the function expressionand optionally its invocation operatorwith the grouping operator,[4] in parentheses, to tell the parser explicitly to expect an expression. Otherwise, in most situations, when the parser encounters the function keyword, it treats it as a function declaration (statement), and not as a function expression.[5] [6] (function);(function);(=>); // With ES6 arrow functions (though parentheses only allowed on outside)

There are other ways to enforce a function expression:!function ;~function ;-function ;+function ;void function ;delete function ;typeof function ;await function ;

In contexts where an expression is expected, wrapping in parentheses is not necessary:let f = function ;true && function ;0, function ;

Passing variables into the scope is done as follows:(function(a, b))("hello", "world");

An initial parenthesis is one case where the automatic semicolon insertion (ASI) in JavaScript can cause problems; the expression is instead interpreted as a call to the last term on the preceding line. In some styles that omit optional semicolons, the semicolon is placed in front of the parenthesis, and is known as a defensive semicolon.[7] [8] For example:a = b + c

(function);...to avoid being parsed as c.

Examples

The key to understanding design patterns such as IIFE is to realize that prior to ES6, JavaScript only featured function scope (thus lacking block scope), passing values by reference inside closures.[9] This is no longer the case, as the ES6 version of JavaScript implements block scoping using the new let and const keywords.[10]

Evaluation context

A lack of block scope means that variables defined inside (for example) a for loop will have their definition "hoisted" to the top of the enclosing function. Evaluating a function that depends on variables modified by the outer function (including by iteration) can be difficult. We can see this without a loop if we update a value between defining and invoking the function.[11] let v, getValue;v = 1;getValue = function ;v = 2;

getValue; // 2

While the result may seem obvious when updating v manually, it can produce unintended results when getValue is defined inside a loop.

Hereafter the function passes v as an argument and is invoked immediately, preserving the inner function's execution context.[12]

let v, getValue;v = 1;getValue = (function (x))(v);v = 2;

getValue; // 1

This is equivalent to the following code:let v, getValue;v = 1;function f(x) ;getValue = f(v);v = 2;

getValue; // 1

Establishing private variables and accessors

IIFEs are also useful for establishing private methods for accessible functions while still exposing some properties for later use.[13] The following example comes from Alman's post on IIFEs.[1]

// "counter" is a function that returns an object with properties, which in this case are functions.let counter = (function);

// These calls access the function properties returned by "counter".counter.get; // 0counter.set(3);counter.increment; // 4counter.increment; // 5

If we attempt to access counter.i from the global environment, it will be undefined, as it is enclosed within the invoked function and is not a property of counter. Likewise, if we attempt to access i, it will result in an error, as we have not declared i in the global environment.

Terminology

Originally known as a "self-executing anonymous function",[14] Ben Alman later introduced the current term IIFE as a more semantically accurate name for the idiom, shortly after its discussion arose on comp.lang.javascript.[1] [15] [16]

Notably, immediately invoked functions need not be anonymous inherently, and ECMAScript5's strict mode forbids arguments.callee,[17] rendering the original term a misnomer.

See also

External links

Notes and References

  1. Web site: Immediately Invoked Function Expressions. Alman. Ben. 15 November 2010. live. https://web.archive.org/web/20171201033208/http://benalman.com/news/2010/11/immediately-invoked-function-expression/. 1 December 2017. 18 January 2019.
  2. Web site: McGinnis . Tyler . JavaScript Modules: From IIFEs to CommonJS to ES6 Modules . ui.dev . 18 August 2021 . en . 15 January 2019.
  3. Book: Lindley, Cody . JavaScript Enlightenment . 2013 . O'Reilly . 978-1-4493-4288-3 . 61.
  4. Web site: Grouping operator . 2 October 2023 . Mozilla Developer Network.
  5. Book: Zakas, Nicholas . Maintainable JavaScript . 2012 . O'Reilly . 978-1-4493-2768-2 . 44.
  6. Web site: ExploringJS . Axel Rauschmayer.
  7. Web site: JavaScript Semicolon Insertion: Everything you need to know . 28 May 2010 . https://web.archive.org/web/20171002224530/http://inimino.org/~inimino/blog/javascript_semicolons . 2 October 2017 . live.
  8. Web site: Semicolons in JavaScript are optional . Mislav . Marohnić . 7 May 2010 . https://web.archive.org/web/20170808231150/https://mislav.net/2010/05/semicolons/ . 8 August 2017 . live.
  9. Book: Haverbeke, Marijn . Eloquent JavaScript . 2011 . No Starch Press . 978-1-59327-282-1 . 29–30.
  10. ECMAScript 6: New Features: Overview & Comparison, Block-Scoped Variables
  11. Web site: Alman . Ben . simple-iife-example.js . Github . 5 February 2013.
  12. Book: Otero . Cesar . Larsen . Rob . Professional jQuery . 2012 . John Wiley & Sons . 978-1-118-22211-9 . 31.
  13. Book: Rettig, Pascal . Professional HTML5 Mobile Game Development . 2012 . John Wiley & Sons . 978-1-118-30133-3 . 145.
  14. Book: Resig, John . Pro JavaScript Techniques . 2006 . Apress . 978-1-4302-0283-7 . 29.
  15. Book: Osmani, Addy . Learning JavaScript Design Patterns . 2012 . O'Reilly . 978-1-4493-3487-1 . 206.
  16. News: Baagoe . Johannes . Closing parenthesis in function's definition followed by its call . 19 April 2010.
  17. Web site: Strict mode . Mozilla JavaScript Reference . Mozilla Developer Network . 4 February 2013.