Home > Web Front-end > JS Tutorial > Detailed explanation of the use of Javascript functions, recursion and closures (execution environment, variable objects and scope chains)_Basic knowledge

Detailed explanation of the use of Javascript functions, recursion and closures (execution environment, variable objects and scope chains)_Basic knowledge

WBOY
Release: 2016-05-16 17:34:15
Original
932 people have browsed it

Function expression

1. There are two ways to define functions in JavaScript:

 1-1. Function declaration:

Copy code The code is as follows:

function funcName(arg1,arg2,arg3){
//Function body
}

 ①name attribute: The function name can be read. Non-standard, browser support: FF, Chrome, Safari, Opera.
 ②Function declaration promotion: means that the function declaration will be read before executing the code. That is, function calls can be placed before function declarations.

 1-2. Function expression:

Copy code The code is as follows:

var funcName = function(arg1,arg2,arg3){
//Function body
};

  ①Anonymous function (anonymous function, or lambda function ): There is no identifier after the function keyword, and the name attribute value is an empty string. Anonymous functions can be used whenever functions are used as values.
 ②Similar to other expressions, function expressions need to be assigned a value before use, so there is no such effect as "function declaration promotion".
 ③Invalid function syntax in ECMAScript:
Copy code The code is as follows:

if judgment Duplicate function declaration in

if(condition){
function sayHi(){
alert("Hi!");
}
} else {
function sayHi(){
alert( "Yo!");
}
}


The browser JavaScript engine corrects the error difference: most browsers will return the second statement, ignoring the condition; FF will return the condition when the condition is Returns the first statement if true.
Use function expressions to solve and implement:
Copy code The code is as follows:

if judgment function expression

var sayHi;
if(condition){
sayHi = function(){
alert("Hi!");
}
} else {
sayHi = function (){
alert("Yo!");
}
}


2. Recursive
Recursive function is a function is formed by calling itself by name.
Copy code The code is as follows:

function factorial(num){ //A classic recursion Factorial function
if (num <= 1){
return 1;
} else {
return num * factorial(num-1);
}
}

  ①If you use the following code to call this function, an error will occur:
Copy the code The code is as follows:

var anotherFactory = factorial;
factorial = null;
alert(anotherFactorial(4));

After saving the factorial() function into the variable anotherFactory, After setting the factorial variable to null, the function is no longer referenced, and the factorial() function needs to be executed in anotherFactorial(4), so an error occurs.
  Use argument.callee (pointer to the function being executed) to solve:
Copy code The code is as follows:

Solution

function factorial(num){
if (num <= 1){
return 1;
} else {
return num * arguments.callee(num-1);
}
}

var anotherFactorial = factorial;
factorial = null;
alert(anotherFactorial(4)); //24


In non-strict mode, when using a recursive function, it is safer to use argument.callee instead of the function name
In strict mode, an error will occur when using argument.callee. Function expressions can be used instead of function declarations:
Copy code The code is as follows:

Function expression replaces function declaration

var factorial = function f(num){
if (num <= 1){
return 1;
} else {
return num * f(num-1);
}
}


4. Closure

refers to a function that has access to variables in the scope of another function. (A common form is function nesting)

Copy code The code is as follows:

function wai(pro ){
return function(obj1,obj2){
var val1 = obj1[pro];
var val2 = obj2[pro];
if(val1 return - ; 🎜>}


When returning an anonymous function, the scope chain of the anonymous function is initialized to include the active object and global variable object of the function. That is, the anonymous function contains the scope of the wai() function.
When each function is called, an execution environment, a variable object and the corresponding scope chain will be created.


4-1. Execution environment and scope

Execution environment execution context, referred to as environment, defines variables and other data that functions have access to, and determines their respective behaviors.
 ①Each execution environment has a variable object, which saves all variables and functions defined by the environment. This object is not accessible from the code, but the parser uses it behind the scenes when processing the data.

  The global variable object is the most peripheral execution environment. It is considered a window object in the web browser, so all global objects and functions are created by the properties and methods of the window object.

After the code in the execution environment is executed, the environment is destroyed, and the variables and function definitions saved in it are also destroyed.  ②When the code is executed in the environment, a scope chain of the variable object will be created to ensure orderly access to all variables and functions that the execution environment has access to.

  The front end of the scope chain is always the variable object of the environment where the currently executed code is located. When the environment is a function, the active object is used as a variable object.

  The active object initially contains only one variable, the argument object.
 The next variable object in the scope chain comes from the containing environment, and the next variable object comes from the next containing environment, until it continues to the global execution environment.

③Identifier parsing: Starting from the previous paragraph, the process of searching for identifiers level by level along the scope chain. 【Not found usually results in an error】


4-2. When the function is created and executed:

Copy the code
The code is as follows:

function compare(val1,val2){ if(val1 return -1; }else if(val1>val2){ return 1;
}else{
return 0;
};
}
var result = compare(5, 10);


 ①When creating the function compare(), a scope chain that pre-contains global variable objects will be created and stored in the internal [[scope]] attribute.
 ②The variable object of the local function compare() only exists during the execution of the function.
When a function is called, an execution environment is created, and the scope chain of the execution environment is built by copying the object in the [[scope]] attribute of the function.
 ③The first time a function is called, such as compare(), an active object containing this, argument, val1 and val2 will be created.
 ④The variable objects of the global execution environment (including this, result, and compare) are second in the scope chain of the compare() execution environment.
 ⑤Scope chain is essentially a list of pointers pointing to variable objects, which only references but does not actually contain the variable objects.
 ⑥ Whenever a variable is accessed in a function, a variable with the corresponding name will be searched in the scope chain.

4-3. Scope chain of closures

A function defined inside another function will add the active object containing the function to its scope chain.
 ①Assigning a function object to null is equivalent to notifying the garbage collection routine to clear it. As the function scope chain is destroyed, its scope chain (excluding the global scope) will also be safely destroyed.
 ②Because closures carry the scope of the containing function, they will take up more memory than other functions.

4-4. Closures and variables

A side effect of scope chaining: closures can only obtain the last value of any variable in the containing function.

Copy code The code is as follows:

function createFunctions(){
var result = new Array();
for (var i=0; i < 10; i ){
result[i] = function(){
return i;
};
}
Return result;
}

①createFunctions() function, assign 10 closures to the result array, and then return the result array. Each closure returns its own index, but all actually return 10.
Since the active object of the createFunctions() function is stored in the scope chain of each function (closure), they refer to the same variable i. When the createFunctions function is executed, the value of i is 10, so the closure The i's in the bag are also all 10.
 ②The solution is to create an anonymous function without using closures and assign the i value to its parameters:
Copy code The code is as follows:

function createFunctions(){
var result = new Array();
for (var i=0; i < 10; i ){
result[i] = function(num){
  🎜> }


Create an anonymous function that will be executed once every time it loops: use the i value surrounding the function each time it loops as a parameter and store it in the anonymous function. Because function parameters are passed by value, not by reference, the num value in each anonymous function is a copy of the i value each time through the loop.


4-5.this object

This object is bound at runtime based on the execution environment of the function.  In the global function, this is equal to window; when the function is called by an object, this is the object.

The execution environment of anonymous functions is global, and its this object usually refers to window. When changing the function execution environment through call() or apply(), this points to its object.  ①When each function is called, it will automatically obtain two special variables: this and argument. When the internal function searches these two variables, it will only search until the expired active object, and it will never be possible to access these two variables of the external function. But by storing the this object in the outer scope in a variable that the closure can access, the closure can access the object.




Copy code

The code is as follows:

クロージャは外部関数の this オブジェクトにアクセスします

var name = "ウィンドウ";

var object = {
name : "My Object",

getNameFunc: function(){
var that = this;
return function(){
return that.name;
};
}
};

alert(object.getNameFunc()()); //"MyObject"


関数を囲む引数オブジェクトには、このメソッドを介してクロージャからアクセスすることもできます。

5. 関数宣言を関数式に変換します

JavaScript は関数宣言の先頭に function キーワードを置きますが、関数宣言の後に括弧を続けることはできないため、function(){......}(); はエラーになります。
関数宣言を関数式に変換するには、関数宣言に括弧のペアを追加します。

コードをコピー コード以下のように:

(function(){
//ブロックレベルのスコープ
})();
source:php.cn
Statement of this Website
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn
Popular Tutorials
More>
Latest Downloads
More>
Web Effects
Website Source Code
Website Materials
Front End Template