学习汤姆大叔《深入理解JavaScript系列》有感(1) —— 立即调用的函数表达式

一. 下面代码用于理解函数的声明调用

function makeCounter() {
    // 只能在makeCounter内部访问i
    var i = 0;

    return function () {
        console.log(++i);
    };
}

// 注意,counter和counter2是不同的实例,分别有自己范围内的i。

var counter = makeCounter();
counter(); // logs: 1
counter(); // logs: 2

var counter2 = makeCounter();
counter2(); // logs: 1
counter2(); // logs: 2
  1. 首先声明了makeCounter函数,该函数中定义了局部变量i,返回值是一个函数,这里要注意的是一个函数的声明;
  2. 使用表达式的方式创建实例,将makeCounter函数的执行结果赋给变量counter,此时counter得到的是makeCounter的返回值,即function () {console.log(++i);};
  3. 因此,counter()表达式中,()的作用就是用于执行function () {console.log(++i);},在控制台中打印出结果。

二. 通过上面的例子,我们有必要认识一下js表达式,用于帮我们理解了立即调用的函数表达式

  1. 表达式分为原始表达式和复杂表达式,上述counter是一个标识符,就是属于原始表达式;
  2. function(){}只是一个函数声明,不属于表达式,因此,在其后面加上(),并不是立即调用函数表达式;
  3. 尽管是命名函数也好,如function fn(){},即使在后面加上(),也无法实现立即执行效果,它同样只是一个函数声明,不属于表达式
  4. 只有把它赋给一个变量,var counter2 = makeCounter();在标识符counter2后面加上(),才是对其进行调用。
  5. 因此,现在的方法就是把函数声明变为表达式,如何转换呢?

三. 书写立即调用的函数表达式的方法,见下面代码:

// 下面2个括弧()都会立即执行
(function () { /* code */ } ()); // 推荐使用这个
(function () { /* code */ })(); // 但是这个也是可以用的
  1. 首先,我们来理解一下小括号()的作用,()除了作为分组运算符应用于数学运算外,在js中,它还有个重要的作用,就是用于区分一个代码是函数声明还是函数表达式,见下面代码:
function func(){};//函数声明方式
(function func(){})//函数表达式方式

结合这段代码和上面的代码,我们就可以清楚的看出,()在代码中的作用,就是将函数声明转换为函数表达式,这就解答了我们上述5中的问题。

  1. 我们也可以通过一个其它的例子来加深理解,这就是eval()方法的使用。该方法的一个常用的应用场景,就是使用eval()函数将json格式字符串转换为对象的时候,需要多嵌套一层小括号。
原文地址:https://www.cnblogs.com/bongxin/p/6343601.html