在 JavaScript 中,圆括号 () 是一种运算符,跟在函数名之后,表示调用该函数。比如,print() 就表示调用 print 函数

有时,我们需要在定义函数之后,立即调用该函数,例如:

function(){ /* code */ }();
// SyntaxError: Unexpected token (

以上代码出现了语法错误
原因是,function 这个关键字即可以当作语句,也可以当作表达式

// 语句
function f() {} // 表达式
var f = function f() {}

其中,JavaScript 引擎规定,如果 function 关键字出现在行首,一律解释成语句

因此,上面错误的代码被认为这一段都是函数的定义,不应该以圆括号结尾,所以就报错了

解决方法就是不要让 function 出现在行首,让引擎将其理解成一个表达式

最简单的处理,就是将其放在一个圆括号里面

// 解决方式一
(function(){ /* code */ }()); // 解决方式二
(function(){ /* code */ })();

上面两种写法都是以圆括号开头,引擎就会认为后面跟的是一个表示式,而不是函数定义语句,所以就避免了错误

这就叫做“立即调用的函数表达式”(Immediately-Invoked Function Expression),简称 IIFE

注意,上面两种写法最后的分号都是必须的。如果省略分号,遇到连着两个 IIFE,可能就会报错

// 报错
(function(){ /* code */ }())
(function(){ /* code */ }())

上面代码的两行之间没有分号,JavaScript 会将它们连在一起解释,将第二行解释为第一行的参数

推而广之,任何让解释器以表达式来处理函数定义的方法,都能产生同样的效果,比如下面三种写法

// 写法一
var i = function(){ return 10; }(); // 写法二
true && function(){ /* code */ }(); // 写法三
0, function(){ /* code */ }();

甚至像下面这样写,也是可以的。

!function () { /* code */ }();
~function () { /* code */ }();
-function () { /* code */ }();
+function () { /* code */ }();

通常情况下,只对匿名函数使用 IIFE

它的目的有两个:一是不必为函数命名,避免了污染全局变量;

二是 IIFE 内部形成了一个单独的作用域,可以封装一些外部无法读取的私有变量。

// 写法一
var tmp = newData;
processData(tmp);
storeData(tmp); // 写法二
(function () {
var tmp = newData;
processData(tmp);
storeData(tmp);
}());

上面代码中,写法二比写法一更好,因为完全避免了污染全局变量

关于立即调用的函数表达式(IIFE)的更多相关文章

  1. 立即调用的函数表达式---IIFE

    有些人则称为“自执行的匿名函数” 在闭包中,我们经常需要使用到匿名函数,我感觉闭包就是一种匿名函数,子集. 但是直接在匿名函数后面调用函数是会出错的.比如: function () { alert(& ...

  2. 立即调用的函数表达式IIFE

    1.写法 (function () { alert("IIFE");})();//或者(function () { alert("IIFE"); }());

  3. 理解JavaScript的立即调用函数表达式(IIFE)

    首先这是js的一种函数调用写法,叫立即执行函数表达式(IIFE,即immediately-invoked function expression).顾名思义IIFE可以让你的函数立即得到执行(废话). ...

  4. 深入理解javascript系列(4):立即调用的函数表达式

    本文来自汤姆大叔 前言 大家学JavaScript的时候,经常遇到自执行匿名函数的代码,今天我们主要就来想想说一下自执行. 在详细了解这个之前,我们来谈了解一下“自执行”这个叫法,本文对这个功能的叫法 ...

  5. [Effective JavaScript 笔记] 第13条:使用立即调用的函数表达式创建局部作用域

    function wrapElements(a){ var res=[],i,n; for(i=0,n=a.length;i<n;i++){ res[i]=function(){return a ...

  6. [JS]深入理解JavaScript系列(4):立即调用的函数表达式

    转自:汤姆大叔的博客 前言 大家学JavaScript的时候,经常遇到自执行匿名函数的代码,今天我们主要就来想想说一下自执行.在详细了解这个之前,我们来谈了解一下"自执行"这个叫法 ...

  7. <深入理解JavaScript>学习笔记(4)_立即调用的函数表达式

    前言 大家学JavaScript的时候,经常遇到自执行匿名函数的代码,今天我们主要就来想想说一下自执行.(小菜理解:的确看到好多,之前都不知道这是自执行匿名函数) 在详细了解这个之前,我们来谈了解一下 ...

  8. js 匿名函数-立即调用的函数表达式

    先提个问题, 单独写匿名函数为什么报错?return 匿名函数 为什么不报错? 如图: 第二种情况在 f 还没有执行的时候,就报错了,,,当然这得归因于函数声明语句声明提前(发生在代码执行之前)的原因 ...

  9. javascript立即调用的函数表达式N种写法(第二篇)

    原文:javascript立即调用的函数表达式N种写法(第二篇) 上一篇博客我谈到将函数声明转换为函数表达式最常见的一种写法是:通过括号()将匿名函数声明转换为函数表达式即(function(){}) ...

随机推荐

  1. VS2015 调试中断点失效或表达式错误的解决办法

    题描述:在调试前加了断点,但debug时红色的断点变成透明的圆圈加一个感叹号,执行到该处时也不会停止. 这个问题遇到过几次了,前几次都没怎么注意,有时候是因为复制粘贴了某段代码后就这样了,然后点击撤销 ...

  2. ETF计算公式:IOPV

    IOPV=(申购.赎回清单中必须现金替代的替代金额+申购.赎回清单中退补现金替代成份证券的数量与最新成交价相乘之和+申购.赎回清单中可以现金替代成份证券的数量与最新成交价相乘之和+申购.赎回清单中禁止 ...

  3. 升级go mod采坑录

    为了使用go mod把golang升级到了最新的1.12版本,go mod是1.11版本引入的,go mod的引入极大的方便了golang项目的依赖管理,同时把golang项目从GOPATH中解放了出 ...

  4. 【Spring Boot学习之二】WEB开发

    环境 Java1.8 Spring Boot 1.3.2 一.静态资源访问 动静分离:动态服务和前台页面图片分开,静态资源可以使用CDN加速;Spring Boot默认提供静态资源目录位置需置于cla ...

  5. 【视频开发】ONVIF客户端搜索设备获取rtsp地址开发笔记(精华篇)

    转载地址:http://blog.csdn.net/gubenpeiyuan/article/details/25618177 概要:           目前ONVIF协议家族设备已占据数字监控行业 ...

  6. css3网站响应式写法

    css3响应式写法因为media不支持ie9以下的浏览器 所有要加个判断<pre> <!-- 全部通用的 --><link rel="stylesheet&qu ...

  7. python:求整数的二进制表示

    求解方法: 1.整数求余 2.重复进行,整数除2再求余,直到除数为0 3.拼接余数 4.反转字符串 def int2two(intNo): twoStr='' if intNo == 0: twoSt ...

  8. arc079

    D. Decrease (Contestant ver.) 大意: 每次操作选一个最大数$-n$,其余数全$+1$. 要求构造一个序列$a$, 使得恰好$k$次操作后最大值不超过$n-1$. 只要让$ ...

  9. oracle查询包含在子表中的主表数据

    Oracle数据库,查询某表中包含在子表中的数据,子表中数据按特定条件来源于该父表,SQL命令如 ) a_table父表,b_table子表,a和b表都有commandId列,a表的commandId ...

  10. 5G和LTE中的HARQ协议

    LTE中有两种重传机制:MAC层的HARQ机制,以及RLC层的ARQ(只针对AM(aknowledgement mode确认模式)数据传输)机制. HARQ: HARQ(HybridAutomatic ...