经典面试题第四更---Event Loop

本文解释了进程与线程的区别,强调了单线程在JS中的优势,介绍了执行栈的工作原理以及浏览器中的EventLoop,区分了消息队列、微任务队列和宏任务。还讨论了Promise和async/await如何影响异步操作的执行。
摘要由CSDN通过智能技术生成

前言:
    🤡 作者简介:我是Morning,计算机的打工人,想要翻身做主人 🙈 🙈 🙈
    🏠 个人主页: Morning的主页
    📕系列专栏:前端面试备战  
    📞 如果小编的内容有欠缺或者有改进,请指正拙著。期待与大家的交流
    🔥如果感觉博主的文章还不错的话,👍点赞👍 + 👀关注👀 + 🤏收藏🤏
 

目录

1.进程与线程

2.执行栈

3.浏览器中的Event Loop


1.进程与线程

面试题:进程与线程的区别?JS单线程带来的好处?

  • 进程与线程都是CPU工作时间片的一个描述。进程是CPU在运行指令及加载保存上下文所需的时间。线程是进程中的更小单位,描述了执行一段指令所需要的时间。(可以理解为在一个浏览器中打开了一个Tab页就是创建了一个进程,其包括多个线程:渲染线程、js引擎线程、HTTP请求线程等等

  • 上文提到了渲染线程JS引擎线程(为互斥线程)在JS运行时可能会阻止UI渲染,因为JS可以修改DOM,如果JS执行的时候UI线程还在工作,就可能导致不能安全的渲染UI。这就是单线程的一个好处,得益于JS是单线程运行的,可以达到节省内存,节约上下文切换时间,没有锁的问题的好处

2.执行栈

面试题:什么是执行栈

可以把执行栈认为是一个存储函数调用的栈结构,遵循后进先出原则 (后执行的函数先弹出栈)

function fn2(){
    throw new Error('error')
}
function fn1(){
    fn2()
}
fn1()

从该报错中可看出,fn2先执行完,fn1再执行完(也是执行栈中的弹出顺序) 

3.浏览器中的Event Loop

 <1>Event Loop开始的时候,会从全局一行一行执行,遇到函数调用,会压入到执行栈中,被压入的函数被称为帧,函数返回后从执行栈中弹出

function fn2(){
    console.log(2);
}
function fn1(){
    console.log(3);
    fn2()
    console.log(4);
}
fn1()

 fn1进入执行栈,输出3   --->   fn2进入执行栈,输出2,弹出执行栈 ---> 输出4,fn1弹出执行栈

<2>.JS中的异步代码,如fetch、setTimeout、setInterval压入到调用栈中的时候里面的消息会进到消息队列。消息队列中的消息会等到调用栈清空之后再去执行

function fn2(){
    console.log(2);
}
function fn1(){
    setInterval(()=>{
        console.log(3);
    },1000)
    fn2()
    console.log(4);
}
fn1()

fn1进入执行栈   --->   setInterval执行(3进入消息队列) setInterval弹出执行栈   --->   fn2进入执行栈,输出2,弹出执行栈 ---> 输出4,fn1弹出执行栈   --->   执行栈清空,输出消息队列中的3

<3>.promise、async、await的异步操作会马上加入到微任务中去,会在调用栈清空的时候立即执行。调用栈中的微任务会立马执行 

var p=new Promise(resolve=>{
    console.log(4);
    resolve(5)
})
function fn1(){
    console.log(1);
}
function fn2(){
    setInterval(()=>{
        console.log('2计时器');
    },1000)
    fn1()
    console.log(3);
    p.then(resolve=>{
        console.log(resolve);
    })
}
fn2()

 new Promise进入执行栈,立即执行,输出4(5进入微任务队列)---> fn2进入执行栈   --->   setInterval执行,(‘2计时器’进入消息队列), setInterval弹出执行栈 ---> fn1进入执行栈,输出1   --->  输出3  ---> 执行栈清空,立即执行微任务队列,输出5 ---> 输出消息队列中的‘2计时器’

疑问:在此篇中我还是有着很多问题,消息队列、微任务队列与宏任务、微任务有什么联系。

什么会进入消息队列,什么进入微任务队列?

希望小伙伴的探讨、指正、答疑

2024.1.25更新  对eventloop又有了新的见解

eventloop,事件循环机制。

事件循环机制的前提是我们要知道js代码是单线程的,为了防止代码阻塞,将代码分为了同步任务和异步任务。同步任务由JS引擎执行,异步任务由宿主环境(浏览器、Node)执行。

同步代码放入执行栈中,异步代码等待时机成熟送入任务队列排队。

在执行栈执行完毕后,会检查任务队列中是否有异步任务,有的话就送到执行栈中执行。再检查,执行,循环往复,这便是事件循环的意义。

在ES6中引入了Promise,此时不需要浏览器JavaScript引擎自身也可以发起异步任务了

因此JS将异步任务又分为了宏任务(事件,网络请求如Ajax,Fetch,定时器)和微任务(Promise,promise本身是同步的,但是catch和then的回调函数是异步的) 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

苏茂林别干饭了

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值