要理解立即执行函数(function(){})(),先了解些函数的基本概念(函数声明、函数表达式、匿名函数)。

函数声明:使用function声明函数,并指定函数名。 

function setFn() {// coding
}

函数表达式:使用function声明函数,但未指定函数名,将匿名函数赋予一个变量。

var setFn = function() {// coding
}

匿名函数:使用function关键字声明函数,但未指定函数名。匿名函数属于函数表达式,匿名函数有很多作用,赋予一个变量则创建函数,赋予一个事件则成为事件处理程序或创建闭包等等。

function() {// coding
}

函数声明与函数表达式的不同在于:

1. 函数声明可在当前作用域下提前调用执行,函数表达式需等执行到该函数后,方可执行,不可提前调用。

setFn()
function setFn() {// coding
}
// 正常,函数声明可提前调用setFn()
var setFn = function() {// coding
}
// 报错,setFn未保存对函数的引用,函数调用需放在函数表达式后面

2. 函数表达式可直接在函数后加括号调用。

var setFn = function() {console.log(2)
}()// 2   解析至此,可直接执行调用

立即执行函数(function(){})()可以看出很像函数表达式的调用,但为什么要加括号呢?如果不加括号:

function(){console.log(1)
}()// 报错,函数需要函数名解析: 虽然匿名函数属于函数表达式,但未进行赋值,所以javascript解析时将开头的function当做函数声明,故报错提示需要函数名

立即执行函数里面的函数必须是函数表达式,所以由var setFn = function() {}()可以理解为在匿名函数前加了 = 运算符后,将函数声明转化为函数表达式,所以拿!,+,-,()...等运算符来测试下是否如此。

!function(){console.log(1)
}()
// 1+function(){console.log(2)
}()
// 2-function(){console.log(3)
}()
// 3(function(){console.log(4)
})()
// 4

由此可见,加运算符确实可将函数声明转化为函数表达式,而之所以使用括号,是因为括号相对其他运算符会更安全,可以减少不必要的麻烦。

立即执行函数与正常函数传参形式是一致的。

(function(a, b){console.log(a + b);
})(1, 2)
// 3

(function(){}())这样写的好处是在内部定义的变量不会跟外部的变量有冲突,达到保护内部变量的作用。jquery等好多库里面就好多使用的这种方式,然后再return一个变量,详情可以查看另一篇博文https://blog.csdn.net/xcymorningsun/article/details/85234232

————————————————————————————————————————————————————

关于保护内部变量闭包问题,这个可以看下面的例子

循环中的闭包

一个常见的错误出现在循环中使用闭包,假设我们需要在每次循环中调用循环序号


for(var i = 0; i < 10; i++) {setTimeout(function() {console.log(i);  }, 1000);
}

上面的代码不会输出数字 0 到 9,而是会输出数字 10 十次。

当 console.log 被调用的时候, 匿名函数保持对外部变量 i 的引用,此时 for循环已经结束, i 的值被修改成了 10.

为了得到想要的结果,需要在每次循环中创建变量 i 的 拷贝

避免引用错误

为了正确的获得循环序号,最好使用 匿名包裹器( 译者注:其实就是我们通常说的自执行匿名函数)。


for(var i = 0; i < 10; i++) {(function(e) {setTimeout(function() {console.log(e);  }, 1000);})(i);
}

外部的匿名函数会立即执行,并把 i 作为它的参数,此时函数内 e 变量就拥有了 i 的一个拷贝。

当传递给 setTimeout 的匿名函数执行时,它就拥有了对 e 的引用,而这个值是 不会被循环改变的。

有另一个方法完成同样的工作;那就是从匿名包装器中返回一个函数。这和上面的代码效果一样。


for(var i = 0; i < 10; i++) {setTimeout((function(e) {return function() {console.log(e);}})(i), 1000)
}

JavaScript——(function(){})()立即执行函数解析相关推荐

  1. js中(function(){…})()立即执行函数写法理解

    js中(function(){-})()立即执行函数写法理解 javascript和其他编程语言相比比较随意,所以javascript代码中充满各种奇葩的写法,有时雾里看花,当然,能理解各型各色的写法 ...

  2. JavaScript中立即执行函数实例详解 转载 作者:李牧羊

    javascript和其他编程语言相比比较随意,所以javascript代码中充满各种奇葩的写法,有时雾里看花,当然,能理解各型各色的写法也是对javascript语言特性更进一步的深入理解.这篇文章 ...

  3. JavaScript 之 立即执行函数

    1.定义 ​ 声明一个函数,并立即调用这个函数,此时这个函数就是立即执行函数,简单来说就是定义函数之后立即执行该函数.立即执行函数一般也写成匿名函数的形式,匿名函数写法为 function(){},就 ...

  4. JavaScript之立即执行函数

    我们知道,在一般情况下,函数必须先调用才能执行,如下所示,我们定义了一个函数,并且调用, function fn(){console.log(1);}fn(); 打印结果为:         如果不调 ...

  5. 全网最详细JavaScript防抖、节流函数解析

    防抖与节流 防抖与节流 防抖 作用与简介 实现 核心与细节 应用场景 节流 作用与简介 实现 核心与细节 应用场景 防抖与节流 防抖 作用与简介 在一个周期T内,如果重复的进行某种响应操作,在不设置防 ...

  6. JavaScript ES6立即执行函数

    立即执行函数 看过jQuery源码的人应该知道,jQuery开篇用的就是立即执行函数.立即执行函数常用于第三方库,好处在于隔离作用域,任何一个第三方库都会存在大量的变量和函数,为了避免变量污染(命名冲 ...

  7. javascript 匿名自执行函数

    有一种匿名函数可以自动执行,这种函数定义如下: (function(){//执行一些语句 })(); 也可以为函数添加参数,语法格式如下: (function(arg_1,arg_2,...arg_n ...

  8. jQuery自执行函数以及封装工具类的方法

    自执行函数 javaScript的自执行函数主要用于保护内部变量不被外部声明污染,自执行函数的结构大致如下:(function(){})();其中,第一个括号使编译器编译该函数体,第二个括号另函数执行 ...

  9. 深入理解javascript中的立即执行函数(function(){…})()

    2019独角兽企业重金招聘Python工程师标准>>> javascript和其他编程语言相比比较随意,所以javascript代码中充满各种奇葩的写法,有时雾里看花,当然,能理解各 ...

最新文章

  1. SMOTE过采样方法
  2. lc171. Excel Sheet Column Number
  3. 前端跨域通信的几种方式
  4. C\C++不经意间留下的知识空白------宏
  5. Spring3.0包描述
  6. MTK 驱动开发(24)---camera模块的制作
  7. 大数据时代时代舍恩伯格书资源_大数据时代的特征和思维
  8. 计算机的五大组成部分(计组学习一)
  9. 全球AI芯片企业排行:英伟达第1,华为第12(七家中国公司入围Top24)
  10. yii2 联表查询时,查询关联表的字段时,使用asArray方法
  11. JavaScript时间格式化工具函数
  12. JDK和JRE安装与下载
  13. 一步一步超级详细的zabbix安装教程
  14. 我是个骄傲的intj
  15. 深度学习(6): RNN
  16. 苹果为M1 MacBook Air/Pro提供自助维修服务 维修成本更低
  17. C++调用Python及间接调用Python三方库
  18. PASCAL VOC2012数据集
  19. 46、W25Q128 存储器工作原理
  20. 腾讯音乐(K歌)的粗排模型

热门文章

  1. Git:本地生成SSH KEY,并关联到git仓库
  2. 计算机 学术论文写作,计算机辅助学术论文写作系统的研制策略与方法.pdf
  3. 使用Mybatis如何对Mysql进行分页功能?
  4. PCL之常用开源数据集汇总
  5. python操作excel命令_python excel操作总结
  6. inception mysql 使用_mysql 审核引擎 goInception 的基本使用
  7. yum -y install php-mysql 版本冲突
  8. spring boot初体验(三)Spring AOP
  9. Shell脚本学习-阶段七-信息过滤磁盘分区
  10. 《深入理解Nginx:模块开发与架构解析》一3.3 如何将自己的HTTP模块编译进Nginx...