由定时器引发的关于JS执行机制的详细了解

由定时器引发的关于JS执行机制的详细了解

问题:若有多个计时器则与设置时间执行不同,为什么?

初见这个问题,自然想到JS的执行机制以及同步与异步,深入了解之后,收获颇丰。下面简单总结一下。

1.JS是单线程非阻塞语言

所谓线程,指的是进程中一个单一顺序的控制流,一个进程中可以并发多个线程,每条线程并行执行不同的任务。而进程是线程的容器。程序是指令、数据及其组织形式的描述,进程则是是程序的实体。

阻塞和非阻塞则关注的是程序在等待调用结果(消息,返回值)时的状态.

阻塞调用: 指调用结果返回之前,当前线程会被挂起。调用线程只有在得到结果之后才会返回

非阻塞调用: 指在不能立刻得到结果之前,该调用不会阻塞当前线程

2.同步和异步

同步操作是放在执行栈中执行,栈遵循先进后出。下面是一个例子:

let A = () => {
    B()
    console.log(1);
};
let B = () => {
    C()
    console.log(2);
};
let C = () => {
    console.log(3);
};
A();//3 2 1

异步操作放在任务队列中。队列遵循先进先出。

当一个任务被执行,js会判断是否为同步任务,如果是同步,压入主线程立即执行;但如果是异步任务,移步异步处理模块(Task Table),当异步任务有了结果,就将异步任务的回调函数注入到任务队列中等待。

当主线程的同步任务执行完毕执行栈为空,js引擎就会读取任务队列中的第一个任务加入到执行执行,当此任务完成,继续重复此类操作,这也就是事件循环

3.定时器

一个简单的定时器:

setTimeout(() => console.log('First'), 3000);

站在宏观思想上理解,这行代码的意思是这个定时器将在三秒后触发,但站在微观的角度上,3000ms并不代表执行时间,而是将回调函数加入任务队列的时间,这也是为何存在定时器执行与所设置等待时间不符的问题所在。

一个例子:

setTimeout(() => console.log('First'), 3000);
setTimeout(() => console.log('Sec'), 3000);

上述代码真正执行是等待三秒后几乎无间隔的同时打印2个结果。

4.关于异步中的宏任务与微任务

宏任务: setTimeout、setInterval、I/O、事件、postMessage、 MessageChannel、setImmediate (Node.js)

微任务: Promise,process.nextTick,MutaionObserver

微任务优先级总是高于宏任务。

附图:

在这里插入图片描述

参考:

JS执行机制

同步与异步,阻塞与非阻塞

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值