为什么会讲这个主题?
这要从一个bug讲起,10月26号,app端,我的考勤日历面板上的信息在ios上显示不全。效果见手机视频。
当时我们几个排查了2-3天都没找到原因,review代码各种改都不行。(此时打开代码看下,src/app/myAttendance/attendance.vue line298 line246)
最后通过setTimeout解决
前两天又遇到一个bug,先给大家看一下,http://jira.worktrans.cn/browse/XBUGXM-2998
部门统计-打卡明细-部门选择器数据加载(src/app/department/pages/detail.vue)
组件位置:src/common/components/dep-emp-select/index.vue
讲下如何修复的
这两个bug都是因为js代码执行时机不当导致的。
由此延伸的JS事件循环机制
参考:https://juejin.im/post/6844903638238756878
首先我们要知道:
- JavaScript是单线程的语言
- Event Loop是javascript的执行机制
javascript事件循环
任务分为两类:
- 同步任务
- 异步任务
先看一段代码:
宏任务:
setInterval()
setTimeout()
微任务:
new Promise()
在一个事件循环中,异步事件返回结果会被放到一个任务队列中。
在当前执行栈为空的时候,主线程会查看微任务队列是否有事件存在。如果不存在,那么再去宏任务队列
中取出一个事件并把对应的回调加入当前执行栈;如果存在,则会依次执行队列中事件对应的回调,知道微任务队列为空,然后去宏任务队列中取出最前面的一个事件,把对应的回调加入当前执行栈……如此反复循环。
同一次事件循环中,微任务永远在宏任务之前执行。
详细的事件循环顺序:
脚本-微任务-渲染
微任务会在执行任何其他事件,或渲染,或执行任何其他宏任务之前完成
事件循环的详细算法:
1. 从宏任务队列(例如script)中出队,并执行最早的任务
2. 执行所有微任务
当微任务队列非空时,出队并执行最早的微任务
3. 执行渲染
4. 如果宏任务队列为空,则休眠直到出现宏任务
5. 转到步骤1
安排一个新的宏任务
使用0延迟的setTimeout(f)
它可被用于将繁重的计算任务拆分成多个部分,以使浏览器能够对用户事件作出反应
标签:分享,队列,JS,任务,循环,事件,执行 From: https://www.cnblogs.com/cathy1024/p/13963505.html