线程和进程
线程和进程是操作系统中的两个概念
- 进程:计算机已经运行的程序。例如我们启动一个应用程序,可能会启动一个或者多个进程。
- 线程:操作系统能够运算的最小单位。每个进程中,都会启动一个线程用来执行程序中的代码,这个线程被称之为主线程。
JavaScript是一门单线程语言。尽管在新的H5规范中提出来Web-worker,但JavaScript作文单线程的核心是没有变化的。所有JavaScript的多线程都是通过单线程模拟出来的。
浏览器中的事件循环机制
事件循环机制可以理解为JavaScript代码和浏览器/Node之间的一个桥梁。
- 浏览器的事件循环机制:我们编写的JavaScript代码和浏览器API调用(settimeout、AJAX、DOM事件)的一个桥梁
- Node的事件循环机制:我们编写的JavaScript代码和系统调用(文件系统、网络系统)之间的桥梁。
主线程和调用栈
JavaScript有一个主线程main thread和一个调用栈。所有的任务都会放在调用栈中等待主线程来执行。
任务队列
任务,可以理解为每一个就是一个任务。
任务分类:
- 同步任务:主线程能立即执行的任务
- 异步任务:需要放在任务队列中等待主线程任务执行完毕后才放在主线程执行的任务
事件循环队列中并不只是维护一个队列,实际上是有两个队列。
- 宏任务队列:ajax、settimeout、setinterval、DOM监听、UI rendering等
- 微任务队列:promise的then回调。queueMicrotask()等
事件循环机制中的执行顺序是怎么样的呢?
- 主线程中的代码优先执行。若主线程代码为空,则进入事件循环队列。
- 优先执行微任务队列中的微任务。若微任务队列为空,则执行宏任务队列中的宏任务。
- 即执行宏任务时,必须保证微任务队列为空。
Node事件循环阶段
node中的事件循环就像是一个桥梁,是连接着应用程序的JavaScript代码和系统调用之间的通道。
无论是文件IO、数据库、网络IO、定时器等在完成相应的操作后,都会将对应的结果和回调函数放到事件循环(任务队列)中。事件循环会不断的从任务队列中取出对应的事件(回调函数)来执行。
一次完成的事件循环分为很多阶段:
main scriptnextTicksother microtasktimersimmediate