盒子
盒子
文章目录
  1. 什么是立即执行函数
  2. 立即执行函数的写法
  3. 立即执行函数的作用
  4. 面试题
  5. 立即执行函数的使用场景
  6. 立即执行函数的参数
  7. 立即执行函数的作用

前端面试之立即执行函数

什么是立即执行函数

声明一个函数,并马上调用这个匿名函数就叫做立即执行函数。在定义好一个函数后,直接执行。

1
(function() {alert('立即执行函数')})()

用声明一个函数,用括号包起来,调用此函数。

立即执行函数的写法

有时候,我们定义函数以后,立即调用该函数,这时不能在函数的定义后面直接加圆括号,这会产生语法错误。产生语法错误的原因是,function这个关键字,既可以当做语句,也可以当做表达式。

1
2
3
4
5
//语句
function fn() {};

//表达式
var fn = function(){};

规定:如果function出现在行首,一律解析成语句。行首是function关键字时,这一段都是函数定义,不应该以圆括号结尾,所以会报错。当不让function出现在行首时,这将被理解为一个表达式,最简单的处理方式就是将其放在一个圆括号里。

1
2
3
4
5
6
7
(function() {
...
}())

(function() {
...
})()

以圆括号开头,这将被理解为表达式,而不是一个函数定义语句,所以就避免了错误,这就叫“立即执行函数”。
其他的写法:

1
2
3
4
5
6
7
8
(function() {alert('匿名函数')}())	//用括号将整个表达式包起来
(function() {alert('匿名函数')})() //用括号将函数包起来
!function() {alert('匿名函数')}()
+function() {alert('匿名函数')}()
-function() {alert('匿名函数')}()
~function() {alert('匿名函数')}()
void function() {alert('匿名函数')}()
new function() {alert('匿名函数')}()

立即执行函数的作用

1、不必为函数命名,避免了污染全局变量。

2、立即执行函数内部形成了一个单独的作用域,可以封装一些外部无法读取的私有变量。

3、封装变量。

面试题

1
2
3
4
5
6
7
var list = document.getElementById("list");
var li = list.children;
for(var i = 0 ;i<li.length;i++){
li[i].onclick=function(){
alert(i); // 结果总是3.而不是0,1,2
}
}

因为i是贯穿整个作用域的,而不是给每一个li分配一个i,点击事件使异步用户一定是在for运行完以后才点击,此时i已经变成3了。

解决方法:

1、使用立即执行函数,给每个li创建一个独立的作用域,在立即执行函数执行的时候,i的值从0到2,对应三个立即执行函数,所以就能正常输出了。

1
2
3
4
5
6
7
var list = document.getElementById("list");
var li = list.children;
for(var i = 0 ;i<li.length;i++){
(function(j) {li[j].onclick=function(){
alert(j); // 结果是0,1,2
}})(i)
}

2、使用ES6的块级作用域

1
2
3
4
5
6
7
var list = document.getElementById("list");
var li = list.children;
for(let i = 0 ;i<li.length;i++){
li[i].onclick=function(){
alert(i); // 结果总是3.而不是0,1,2
}
}

立即执行函数的使用场景

1、代码在页面加载完成之后,不得不执行一些设置工作,比如时间处理器,创建对象等等。

2、所有的这些动作只需要执行一次,比如只需要显示一个事件。

3、将代码包裹在它的局部作用域中,不会让任何变量泄漏成全局变量。

立即执行函数的参数

1
2
3
(function(i) {
...
})(j)

如果立即执行函数中需要全局变量,全局变量会被作为一个参数传递给立即执行函数。j代表是实参,i代表的是执行函数的形参。

立即执行函数的作用

1、改变变量的作用域(创建一个独立的作用域)。

2、封装临时变量。

欢迎关注公众号
扫码关注我的微信公众号-大前端合集
  • 微信公众号-大前端合集