JS Closed Package

Source: Internet
Author: User

Closures are the characteristics of many languages, in JS, closures are mainly related to JS a few other features: scope chain, garbage (memory) recycling mechanism, function nesting, and so on.

Prior to understanding closures. It is better to understand the meaning of the scope chain, simply speaking, the scope chain is the function at the time of definition created, to find the value of the variable used in an index, and his internal rule is to put the function of its own local variables in the first, the parent function of its own variables in the second, Put the variables in the higher-level function later, and so on until the global object. When the function needs to query the value of a variable, the JS interpreter will go to the scope chain to find, from the first local variable to find, if not found the corresponding variable, then to the next level of the chain to find, once the variable is found, will no longer continue. If the required variable is not found at the end, the interpreter returns undefined.

Understanding the scope chain, we look at the JS memory recovery mechanism, in general, a function at the beginning of execution, it will be defined in the variable memory space to save, in case of the subsequent statements to use, wait until the function is finished to return, These variables are considered useless. The corresponding memory space is also recycled. The next time the function is executed, all the variables return to their original state and are re-assigned. But if another function is nested inside the function, And this function is likely to be called externally. And this internal function uses some variables of the external function. This memory-recycling mechanism can cause problems. If an intrinsic function is called directly after the external function returns, the Then the intrinsic function cannot read the value of the variable in the external function that he needs. So the JS interpreter will automatically save the function and the variables he or she may use, including the local variables and the variables (free variables) of the parent and ancestor-level functions, when it encounters the function definition. That is, to build a closure, These variables will not be reclaimed by the memory collector, but only if the internal function is not possible to be called (for example, if it is deleted, or if there is no pointer), the closure will be destroyed, and no one of the closure references will be recycled when the next memory recycle starts.

In other words, with closures, nested function structures work, which is what we expect. Then, closures have some features that are often difficult for programmers to understand.

Take a look at the following section of code.

var result=[];function foo () {    var i= 0;    for (; i<3;i=i+1) {        result[i]=function () {            alert (i)        }    }};foo (); result[0] ();//3result[1] ();// 3RESULT[2] (); 3

In this code, the programmer wants the variable i in the Foo function to be used by the inner loop function, and can get their index separately, and in fact, only the value that the variable is last reserved, that is. The free variable that is recorded in the closure is just a reference to the variable, not the value of the variable, when the variable is changed , the value of the variable obtained in the closure will also be changed.

One way to do this is to have the inner function execute as soon as the loop is created, capture the current index value, and then record it in one of its own local variables. Then, using the return function method, rewrite the intrinsic function, let the next call, return the value of the local variable, the improved code:

var result=[];function foo () {    var i= 0;    for (; i<3;i=i+1) {        result[i]= (function (j) {            return function () {                alert (j);            };        }) (i);}    ; Foo (); result[0] (); 0RESULT[1] (); 1RESULT[2] (); 2

I'll explain it here again. 2 additional techniques are used, and the anonymous and return functions are immediately called

But you just need to know two things about the application--the function as the return value, and the function as a parameter pass.

First, the function as the return value

As the above code, the bar function is assigned to the F1 variable as the return value. When executing F1 (15), the value of the max variable under the FN scope is used. As for how to take values across scopes, you can refer to the previous section.

Second, the function is passed as a parameter

As in the code above, the FN function is passed as one parameter into another function, assigned to the F parameter. When you execute F (15), the value of the max variable is 10, not 100.

In the previous section, when the free variable was evaluated across scope, it was emphasized that the scope of the function should be created instead of the parent scope. Understand this, in the above two-way code, how the free variable value should be relatively simple. (Do not understand the friend must go to the last section to see, this is very important!) )

In addition, when it comes to closures, you need to combine the execution context stack with a combination of scopes.

When executing the context stack (http://www.cnblogs.com/wangfupeng1988/p/3989357.html), we mentioned that when a function is called, its execution context is destroyed and the variables are destroyed at the same time.

But there was a question mark in that article at the time-in some cases, after the function call was completed, its execution context was not destroyed. This is what is needed to understand the core of closures.

We can take the first paragraph of this article (slightly modified) to analyze the code.

The first step is to generate the global context environment before the code executes and assign values to the variables at execution time. The global context environment is active at this time.

The second step, when executing the 17th line of code, calls FN (), produces the FN () execution context, presses the stack, and sets the active state.

The third step, after executing line 17th, the FN () call is complete. It is supposed to destroy the execution context of FN (), but this cannot be done here. Note that the emphasis is on: Because a function is returned when the FN () is executed. The special thing about functions is that you can create a separate scope. And coincidentally, in the body of the returned function, there is also a free variable Max to refer to in the FN () context under the FN scope. Therefore, this max cannot be destroyed, and Max in the bar function will not be able to find the value after destroying it.

Therefore, the FN () context here cannot be destroyed and still exists in the execution context stack.

-that is, when the 18th row is executed, the global context becomes active, but the FN () context is still in the execution context stack. In addition, when you finish line 18th, Max in the global context environment is assigned a value of 100. Such as:

Fourth, executes to line 20th, executes F1 (15), that is, executes bar (15), creates a bar (15) context, and sets it to the active state.

When you execute bar (15), Max is a free variable and needs to be found in the scope where the bar function was created, and the value of Max is 10. This process has been mentioned in the scope chain section.

The point here is that creating the bar function is created when you execute FN (). FN () has long been executed, but the FN () execution context still exists with the stack, so when bar (15), Max can find it. If the FN () context is destroyed, then Max cannot find it.

Using closures increases the cost of content, and now it's obvious!

The fifth step, the execution of 20 lines is the context of the destruction process, here will not repeat.

Closures and scope, contextual environment has an inseparable relationship, really is "want to say love you not easy"!

In addition, closures are very much used in jquery, and there are a few examples here. So, whether you want to know a classic framework/class library, or want to develop a plug-in or class library, like closures, prototypes of these basic theories, it must be known. Otherwise, you do not know why, because the bugs may be completely outside your knowledge.

JS Closed Package

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.