前言
他来了他来了,前端必问题之一来了
一、什么是单线程?
就是至上而下,按照顺序走,前面执行了,后面的才会执行
二、为什么JS是单线程?
- 好处:单线程的特点能更好的提高运行效率
- JS用法层面:JS的主要用途是与用户互动和dom操作。这决定了它只能是单线程,否则会带来很复杂的同步问题。如:若JS有多个线程,一个操作一个节点,另一个删除那个节点,要先走哪一步?
三、任务队列
由上面的单线程问题,我们知道JS是单线程的,有点像是同步操作的一个逻辑,一个页面,由同步操作又有异步操作,要怎么安排,怎么触发呢?这就扯到了,任务队列的问题。
1. 什么是任务队列
任务队列就相当于一个临时存放异步任务的储存栈,他首先会执行主线程的同步任务,当主线程遇到异步任务,就会先把异步任务先放在任务队列里,等到同步任务全部执行完,再去执行任务队列里面的异步任务。
2. 什么是微任务宏任务
通俗点讲,微任务就是同步任务,宏任务就是异步任务,例如
- 微任务:Promise(async/await)、简单的console.log啥的
- 宏任务:定时器、事件绑定、ajax、回调函数
四、常见面试题例子
async function async1(){
console.log(1)
const result = await async2()
console.log(3)
}
async function async2(){
console.log(2)
}
Promise.resolve().then(()=>{
console.log(4)
})
setTimeout(() => {
console.log(5)
});
async1()
console.log(6)
正确的顺序为:1、2、6、4、3、5
- 首先我们由上知道async事件和Promise都相当于优先执行的微任务,而计时器为宏任务
- 所以,先执行async1中输出‘1’,紧接着就输出‘2’
- 此时await事件还没有返回结果,所以‘3’还不能输出,而promise中的.then又要在等一轮,所以执行console.log(6)
- 第一轮执行完后,再来第二轮,此时await已返回可以输出’3’.但是async1在后面才调用,所以先执行.then输出‘4’
- 然后执行async1,await返回输出‘3’
- 最后再执行宏任务输出‘5’
总结
以上就是今天的全部内容,下次再见呐!😛