Is it true that a closure is created in the following cases for foo
, but not for bar
?
Case 1:
<script type="text/javascript">
function foo() { }
</script>
foo
is a closure with a scope chain with only the global scope.
Case 2:
<script type="text/javascript">
var i = 1;
function foo() { return i; }
</script>
same as Case 1.
Case 3:
<script type="text/javascript">
function Circle(r) {
this.r = r;
}
Circle.prototype.foo = function() { return 3.1415 * this.r * this.r }
</script>
in this case, Circle.prototype.foo
(which returns the circle's area) refers to a closure with only the global scope. (this closure is created).
Case 4:
<script type="text/javascript">
function foo() {
function bar() {
}
}
</script>
here, foo
is a closure with only the global scope, but bar
is not a closure (yet), because the function foo
is not invoked in the code, so no closure bar
is ever created. It will only exist if foo
is invoked , and the closure bar
will exist until foo
returns, and the closure bar
will then be garbage collected, since there is no reference to it at all anywhere.
So when the function doesn't exist, can't be invoked, can't be referenced, then the closure doesn't exist yet (never created yet). Only when the function can be invoked or can be referenced, then the closure is actually created?
A closure is when free variables in some function code are bound to some values by the function "context" (closure being a more proper term here than context).
<script type="text/javascript">
var i = 1;
function foo() { return i; }
</script>
Here, i
is a free variable for the function code of foo
. And this free variable is not bound to any particular value by any existing context (closure). So you don't have any closure.
<script type="text/javascript">
var i = 1;
function foo() { return i; }
foo(); // returns 1
i = 2;
foo(); // returns 2
</script>
Now to create a closure you have to provide a value-bounding context:
<script type="text/javascript">
function bar() {
var i = 1;
function foo() { return i; }
return foo;
}
bar(); // returns function foo() { return i; }
bar()(); // returns 1
// no way to change the value of the free variable i => bound => closure
</script>
In summary, you can't have a closure unless a function returns another function. In that case, the returned function has all the variable-value bindings that existed in the returning function when it exited.
<script type="text/javascript">
function bar() {
var i = 1;
function foo() { return i; }
i = 2;
return foo;
}
bar()(); // returns 2
</script>
Concerning your exemples:
this
. When the function is called as member of an object, the object is assigned to the value of this
. Otherwise, the value of this
is the global object.foo
return bar
, you would create a closure that contains only 'bar' and its value : function bar() {}
.closure bar will exist until foo returns, and the closure bar will then be garbage collected, since there is no reference to it at all anywhere
Yes.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With