[HtmlCssJs] 2024-04-29 圈点102
摘要:js中延时执行的逻辑思维理解(同时可理解闭包)
js中延时执行的逻辑思维理解(同时可理解闭包)
js在正常情况下是按照顺序依次执行的,不存在延时执行的功能问题。其实延时和闭包也有非常大的关系,延时功能的制作也用到了闭包的功能。
在实际应用中很多时候,却需要延时的功能,怎么处理?先理解一下JS延时逻辑,通过几个例子分析;
示例1:
for(var i = 0; i < 3; i++) {
setTimeout(function() {
console.log(i);
}, 1000);
}
结果为3个3,而且差不多是在瞬间显示3个3,为什么呢?
问题1,为什么显示的数字是3?
问题2,为什么差不多是同时瞬间显示呢?
因为在循环时,循环到setTimeout时,JS主线程并不会停止等待setTimeout的完成再继续执行下面的命令,而是分出一个支线程去等待1秒钟再执行setTimeout中的函数体;
所以上面执行的流程是:
主线程一直在循环i,并累计i+1;
因为循环了三次,所以会生成三个setTimeout支线执行三次函数体,所以会显示3个数.
因为i从0循环到3的时间非常短,短于间隔1000毫秒,所以i最终是3,所以这个显示的数就是3.
循环的时间非常快,且都在1000毫秒后执行,所以显示出来时也差不多瞬间显示完成。
如果循环的次数非常大,那么显示的这个数字就会不太确定。
示例2:
for(var i = 0; i < 3; i++) {
setTimeout(function() {
console.log(i);
}, (i+1)*1000);
}
结果为3个3,而且差不多每隔1000毫秒显示1个3。
为什么显示的是数字3的原理同示例1.
为什么会差不多每隔1000毫秒显示呢?
因为分别有三个setTimeout支线程去执行,第一个是间隔1000毫秒,第二个是间隔2000毫秒,第一个是间隔3000毫秒,所以会每隔一秒显示数字3.
示例3:
for(var i = 0; i < 3; i++) {
(function(i){
console.log(i);
setTimeout(function() {
console.log(i);
}, (i+1)*1000);
})(i)
}
结果为每隔1000毫秒依次显示0,1,2。为什么呢?
很明显,就会间隔1000毫秒依次显示出i的值。其实这里用到了闭包函数的问题。
分析过程(示例1,2,3都适用这个过程):
主线程进入循环:
当i=0时,调用函数,并在1000毫秒后显示i; 然后继续循环(不会等待),
当i=1时,调用函数,并在2000毫秒后显示i; 然后继续循环(不会等待),
当i=2时,调用函数,并在3000毫秒后显示i; 然后继续循环(不会等待),
当i=3时,结束循环。
1秒后,执行函数显示i;
2秒后,执行函数显示i;
3秒后,执行函数显示i;
区别在于示例3中在i=3后,即结束循环后,执行的是闭包函数;所以其i显示是传递值,而不是循环中的值。这三个示例也可以用于JS的闭包函数的理解。
js在正常情况下是按照顺序依次执行的,不存在延时执行的功能问题。其实延时和闭包也有非常大的关系,延时功能的制作也用到了闭包的功能。