技术频道导航
HTML/CSS
.NET技术
IIS技术
PHP技术
Js/JQuery
Photoshop
Fireworks
服务器技术
操作系统
网站运营

赞助商

分类目录

赞助商

最新文章

搜索

关于JavaScript闭包的5个面试问题,你能回答吗?

作者:admin    时间:2022-6-8 17:2:46    浏览:

在前端JavaScript面试中,闭包是经常被问到的概念。在本文中,我收集了关于JavaScript闭包的5个面试问题,你能否回答?

1、下面哪个函数访问外部范围变量?

A:

let countClicks = 0;
button.addEventListener('click', function clickHandler() {
  countClicks++;
});

B:

const result = (function immediate(number) {
  const message = `number is: ${number}`;
  return message;
})(100);

C:

setTimeout(function delayedReload() {
  location.reload();
}, 1000);

答案

clickHandler countClicks 从外部范围访问变量。

immediate 不从外部范围访问任何变量。

delayedReload location从全局范围(也就是最外层范围)访问全局变量。

所以答案是:A

2、以下代码片段在控制台输出的是什么记录?

(function immediateA(a) {
  return (function immediateB(b) {
    console.log(a); // 记录什么?
  })(1);
})(0);

答案

0被记录到控制台。查看演示

immediateA用参数调用0,因此a参数是0

immediateB是嵌套在aimmediateA函数中的函数,是一个从外部范围immediateA捕获变量的闭包,其中a0。因此console.log(a)等于0

3、以下代码片段控制台记录什么?

let count = 0;
(function immediate() {
  if (count === 0) {
    let count = 1;
    console.log(count); // 记录什么?
  }
  console.log(count); // 记录什么?
})();

答案

10记录到控制台。查看演示

第一条语句let count = 0声明了一个变量count

immediate()是一个从外部范围捕获变量count的闭包。immediate()函数范围内count0

但是,在条件内部,另一个let count = 1声明了一个局部变量coun,它把外部范围的count覆盖。第一个console.log(count)日志是1

第二个console.log(count)日志是0,因为这里count的变量是从外部范围访问的。

4、以下代码片段控制台记录什么?

for (var i = 0; i < 3; i++) {
  setTimeout(function log() {
    console.log(i); // 记录什么?
  }, 1000);
}

答案

333记录到控制台。查看演示

代码片段分两个阶段执行。

阶段1

for()迭代 3 次。在每次迭代期间,都会log()创建一个新函数,该函数捕获变量isetTimout()计划log()在 1000 毫秒后执行。

for()循环完成时,i变量具有值3

阶段2

第二阶段发生在 1000 毫秒后:

setTimeout()执行预定的log()功能。log()读取变量的当前值i,即3,并记录到控制台3

这就是为什么333被记录到控制台了。

挑战一下:如何在经过 1 秒后将此示例修复为记录0、1值?

5、以下代码片段控制台记录什么?

function createIncrement() {
  let count = 0;
  function increment() { 
    count++;
  }
  let message = `Count is ${count}`;
  function log() {
    console.log(message);
  }
  
  return [increment, log];
}
const [increment, log] = createIncrement();
increment(); 
increment(); 
increment(); 
log(); // 记录的是什么?

答案

Count is 0被记录到控制台。查看演示

increment()函数已被调用 3 次,有效地递增count的值到3。

message变量存在于createIncrement()函数的范围内。其初始值为Count is 0。但是,即使count变量已经增加了几次,message变量总是保持不变Count is 0

log()函数是一个从createIncrement()作用域捕获message变量的闭包。console.log(message)记录到控制台是Count is 0

挑战一下:如何修复log()函数以返回具有实际count值的消息?

总结

本文收集了5个有关javascript闭包的面试问题,通过针对这些问题的解释,你对闭包概念的理解应该会更进一步。

相关文章

标签: 闭包  
x
  • 站长推荐