Content deleted Content added
m →External links: HTTP to HTTPS for Blogspot |
|||
(15 intermediate revisions by 12 users not shown) | |||
Line 10:
[[Peter Landin]] defined the term ''closure'' in 1964 as having an ''environment part'' and a ''control part'' as used by his [[SECD machine]] for evaluating expressions.<ref name=landin>
{{cite journal |last=Landin |first=P.J. |author-link=Peter Landin |title=The mechanical evaluation of expressions |journal=The Computer Journal |volume=6 |issue=4 |date=January 1964 |pages=308–320 |doi=10.1093/comjnl/6.4.308 |url=https://academic.oup.com/comjnl/article-pdf/6/4/308/1067901/6-4-308.pdf }}</ref> [[Joel Moses]] credits Landin with introducing the term ''closure'' to refer to a [[Anonymous function|lambda expression]] with open bindings (free variables) that have been closed by (or bound in) the lexical environment, resulting in a ''closed expression'', or closure.<ref>
{{cite journal |last=Moses |first=Joel |author-link=Joel Moses |date=June 1970 |title=The Function of FUNCTION in LISP, or Why the FUNARG Problem Should Be Called the Environment Problem |journal=ACM
Sussman and [[Harold Abelson|Abelson]] also use the term ''closure'' in the 1980s with a second, unrelated meaning: the property of an operator that adds data to a [[data structure]] to also be able to add nested data structures. This use of the term comes from [[Closure (mathematics)|mathematics use]], rather than the prior use in computer science. The authors consider this overlap in terminology to be "unfortunate."<ref>{{cite book |last1=Abelson |first1=Harold |author1-link=Harold Abelson |last2=Sussman |first2=Gerald Jay |author2-link=Gerald Jay Sussman |last3=Sussman |first3=Julie |author3-link=Julie Sussman |date=1996 |title=Structure and Interpretation of Computer Programs |url=https://mitpress.mit.edu/sites/default/files/sicp/full-text/book/book.html |publisher=MIT Press |pages=98–99 |isbn=0-262-51087-1}}</ref>
Line 46:
The nested function definitions are not themselves closures: they have a free variable which is not yet bound. Only once the enclosing function is evaluated with a value for the parameter is the free variable of the nested function bound, creating a closure, which is then returned from the enclosing function.
Lastly, a closure is only distinct from a function with free variables when outside of the scope of the non-local variables, otherwise the defining environment and the execution environment coincide and there is nothing to distinguish these (static and dynamic binding cannot be distinguished because the names resolve to the same values). For example, in the
<syntaxhighlight lang="python">
x = 1
Line 59:
This is most often achieved by a function return, since the function must be defined within the scope of the non-local variables, in which case typically its own scope will be smaller.
This can also be achieved by [[variable shadowing]] (which reduces the scope of the [[non-local variable]]), though this is less common in practice, as it is less useful and shadowing is discouraged. In this example <code>f</code> can be seen to be a closure because <code>x</code> in the body of <code>f</code> is bound to the <code>x</code> in the global namespace, not the <code>x</code> local to <code>g</code>:
<syntaxhighlight lang="python">
x = 0
Line 102:
</syntaxhighlight>
The arrow operator <code>=></code> is used to define an [https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions/
A function may create a closure and return it, as in this example:
Line 203:
===Example 2: Accidental reference to a bound variable===
For this example the expected behaviour would be that each link should emit its id when clicked; but because the variable 'e' is bound to the scope above, and lazy evaluated on click, what actually happens is that each on click event emits the id of the last element in 'elements' bound at the end of the [[for loop]].<ref>{{cite web |title=Closures |url=https://developer.mozilla.org/en-US/docs/Web/JavaScript/Closures#Creating_closures_in_loops_A_common_mistake |website=MDN Web Docs |access-date=20 November 2018}}</ref>
<syntaxhighlight lang="javascript">
var elements = document.getElementsByTagName('a');
Line 541:
=== Function objects (C++) ===
[[C++]] enables defining [[function object]]s by overloading <code>operator()</code>. These objects behave somewhat like functions in a functional programming language. They may be created at runtime and may contain state, but they do not implicitly capture local variables as closures do. As of [[C++11|the 2011 revision]], the C++ language also supports closures, which are a type of function object constructed automatically from a special [[language construct]] called ''lambda-expression''. A C++ closure may capture its context either by storing copies of the accessed variables as members of the closure object or by reference. In the latter case, if the closure object escapes the scope of a referenced object, invoking its <code>operator()</code> causes undefined behavior since C++ closures do not extend the lifetime of their context.{{main|
<syntaxhighlight lang="cpp">
Line 583:
== See also ==
{{div col}}
* [[Command pattern]]
* [[Currying]]
Line 589 ⟶ 590:
* [[Syntactic closure]]
* [[Value-level programming]]
{{div col end}}
== Notes ==
Line 602 ⟶ 604:
|date=2007-01-28
|title=A Definition of Closures
|url=
}}
* {{cite web
|