在【异步 & 进程 & Promise规范及应用-优快云博客】一文中,介绍了异步与进程的关系,以及promise的规范以及应用,这里对异步执行顺着做一个扩展。
JavaScript是单线程语言,同一时间只能做一件事,只有当前一个任务结束,才会执行下一个任务。假如前一个任务执行时间较长,下一个任务还得等待前一个任务执行完成。
在JS中有同步任务和异步任务,他们之间的执行有一定的顺序。
Event Loop事件循环
关于事件循环,在【异步 & 进程 & Promise规范及应用-优快云博客】一文中也有提到。
在JS中把任务分为同步任务和异步任务:
1、同步任务(synchronous):在主线程(执行栈)中排队执行的任务,只有前一个任务执行完毕,才能执行下一个任务
2、异步任务(asynchronous):在任务队列(task queue)中,当任务队列通知主线程,某个异步任务能够执行了,该任务才会进入主线程(执行栈)中执行。
事件循环机制:
(1)当执行JS代码时,同步任务会被推入执行栈中执行。
(2)当异步操作(setTimeout,promise,XMLHttpRequest等)执行完成时,它们的回调函数会被推入任务队列。
(3)检查执行栈是否为空,如果为空,则从任务队列中取出第一个任务,推入执行栈执行。当执行栈中所有同步任务执行完毕,则会读取任务队列,异步任务结束等待状态,进入执行栈,开始执行。任务队列中任务执行完成后,继续回到执行栈进行下一轮任务执行。
任务队列
任务队列(也叫事件队列)分为宏任务队列(macrotask queue)和微任务队列(microtask queue)。JavaScript引擎遵循事件循环机制,在执行完当前宏任务后,会检查微任务队列,执行微任务,然后再取下一个宏任务执行,从而形成了事件循环。【有微则微、无微则宏】
宏任务:所有同步任务、I/O操作、setTimeout、setInterval、setImmediate(Node.js环境)、requestAnimationFrame、事件监听回调函数等
微任务:Promise的then、catch、finally;async/await中的代码;Generator函数、MutationObserver、process.nextTick(Node.js 环境)
特殊任务:
requestAnimationFrame(callback)-仅仅存在于浏览器环境,执行时机在setTimeout之前执行(第一次宏微任务执行完成后,在下一次宏任务之前执行)【与UI渲染