js的异步和单线程
最近,同事之间做技术分享的时候提到了一个问题“js的异步是另开一个线程吗?”当时为此争论不休。会后自己查阅了一些资料,对这个问题进行一个自我的分析与总结,有不同意见的希望可以赐教,谢谢!
js的异步主要有三部分:定时器setTimeout/setInterval;HTTP请求;事件响应。
对于定时器setTimeout/setInterval的异步问题,高程上《高级定时器》(P609)是这样解释的:
除了主JavaScript执行进程外,还需要一个在进程下一次空闲时执行的代码队列。随着页面生命周期推移,代码会按照执行顺序添加入队列,例如当按 钮被按下的时候他的事件处理程序会被添加到队列中,并在下一个可能时间内执行。在接到某个Ajax响应时,回调函数的代码会被添加到队列。JavaScript中没有任何代码是立即执行的,但一旦进程空闲则尽快执行。定时器对队列的工作方式是当特定时间过去后将代码插入,这并不意味着它会马上执行,只能表示它尽快执行。
定时器对队列的工作方式是当特定时间过去后将代码插入,这并不意味着它会马上执行,只能表示它尽快执行。定时器对队列的工作方式是,当特定的时间过去后,将代码插入,注意添加到队列并不意味着它会马上执行,而只能说它会尽快执行,设定一个150ms后执行的定时器,不代表150ms后它会马上执行,它只会表示在150ms后被加入到队列中,如果这个时间点队列是空闲的,那么这段代码就会被执行;其他情况下,代码可能明显地等待更长时间才执行。
总结:
Javascript引擎解析是一个单线程的过程,浏览器无论在任何时候有且只有一个线程在运行Javascript程序;
- 浏览器是多线程的,这些线程在内核控制下相互配合以保持同步。在处理js的异步上浏览器内核的实现可能有多个进程:Javascript引擎线程、界面渲染线程、浏览器事件触发线程、HTTP请求线程…… 补充 : 这些线程的名字为渲染引擎、网络、js解析器等 参考自 前端必读:浏览器内部工作原理
Javascript除了一个主线程外,还配有一个代码队列,这个队列用以存放定时器、HTTP请求、事件响应的回调。
所以我对这个流程的理解是这样的:
Javascript代码自上而下执行的,当执行到定时器、或者发送HTTP请求、或者发生用户交互事件响应时,会自动触发对应事件(HTTP请求、事件响应),将回调函数储存到队列中。Javascript执行完主线程代码后,会去执行任务队列,队列内这个时间点是否有代码要执行;如果有,则执行队列中的代码。
进一步理解——对队列:
有细心的会发现,上面的理解没有加入"定时器",我对此的进一步理解: 有一个现象,Javascript里提供了console.time(name)
和console.timeEnd(name)
可以打印出一段代码的执行时间。由此,我感觉Javascript每一段代码的执行都会有记录一个时间。Javascript会根据这个时间来安排队列.
当代码执行到用户交互事件时,会传入回调给队列,该回调的时间就是事件触发的时间;当代码执行到定时器的时候,传入队列的回调函数的时间是定时器触发的时间加上延迟;而HTTP请求传递给队列的回调函数的时间则是其取得数据的时间(我感觉中间可能穿插了一个readyState==4
时会重新传入一个时间,或者可以直接抛去时间,做if判断,判断状态是4时执行);这样可以根据时间对队列进行进一步排序,形成一个自上而下的队列!
js的异步和单线程的更多相关文章
- 探秘JS的异步单线程
对于通常的developer(特别是那些具备并行计算/多线程背景知识的developer)来讲,js的异步处理着实称得上诡异.而这个诡异从结果上讲,是由js的“单线程”这个特性所导致的. 我曾尝试用“ ...
- 面试 09-02.js运行机制:异步和单线程
09-02.js运行机制:异步和单线程 #前言 面试时,关于同步和异步,可能会问以下问题: 同步和异步的区别是什么?分别举一个同步和异步的例子 一个关于 setTimeout 的笔试题 前端使用异步的 ...
- JS(异步与单线程)
JS(异步与单线程) 题目1.同步和异步的区别是什么,试举例(例子见知识点) 区别: 1.同步会阻塞代码执行,而异步不会 2.alert 是同步,setTimeout 是异步 题目2.关于 setTi ...
- JS三座大山再学习(三、异步和单线程)
本文已发布在西瓜君的个人博客,原文传送门 前言 写这一篇的时候,西瓜君查阅了很多资料和文章,但是相当多的文章写的都很简单,甚至互相之间有矛盾,这让我很困扰:同时也让我坚定了要写出一篇好的关于JS异步. ...
- JS三座大山再学习 ---- 异步和单线程
本文已发布在西瓜君的个人博客,原文传送门 前言 写这一篇的时候,西瓜君查阅了很多资料和文章,但是相当多的文章写的都很简单,甚至互相之间有矛盾,这让我很困扰:同时也让我坚定了要写出一篇好的关于JS异步. ...
- 【译】深入理解python3.4中Asyncio库与Node.js的异步IO机制
转载自http://xidui.github.io/2015/10/29/%E6%B7%B1%E5%85%A5%E7%90%86%E8%A7%A3python3-4-Asyncio%E5%BA%93% ...
- JS的异步世界
前言 JS的异步由来已久,各种异步概念也早早堆在开发者面前.可现实代码中,仍然充斥了各种因异步顺序处理不当的bug,或因不好好思考,或因不了解真相.今天,就特来再次好好探索一番JS的异步世界. 01 ...
- JavaScript异步和单线程
一,同步和异步的区别: 同步会阻塞代码执行,而异步不会.(比如alert是同步,setTimeout是异步) 二,前端使用异步的场景: 1,定时任务:setTimeout,setInterval 2, ...
- JS的异步模式
JS的异步模式:1.回调函数:2.事件监听:3.观察者模式:4.promise对象 JavaScript语言将任务的执行模式可以分成两种:同步(Synchronous)和异步(Asychronous) ...
随机推荐
- 不可不知的表达式树(3)定制IQueryProvider
前面我们说到利用表达式树技术实现LINQ-to-SQL,实际上可以针对任何数据源,实现LINQ-to-Everything.这里还涉及到两个重要的接口即IQueryable和IQueryProvide ...
- 三大家族(offset、scroll、client)
offset.scroll.client三大家族 offset家族 offsetWidth 与 offsetHeight offset 偏移 用于获取元素自身的位置和大小 offsetWidth和of ...
- 如何编写高效的jQuery代码(转载)
jQuery的编写原则: 一.不要过度使用jQuery 1. jQuery速度再快,也无法与原生的javascript方法相比,而且建立的jQuery对象包含的信息量很庞大.所以有原生方法可以使用的场 ...
- ftp无法上传问题
1.背景 ftp服务端和客户端一直未做任何改动,无法上传属于突发状态,除此客户端外其他客户端上传正常 客户端(SunOS系统)可以正常连接ftp的xxx21端口,但是传输数据(文件)时无法正常传输 上 ...
- (转)Jquery获取上级、下级或者同级的元素
下面介绍JQUERY的父,子,兄弟节点查找方法 jQuery.parent(expr) 找父亲节点,可以传入expr进行过滤,比如$("span").parent()或者$(&qu ...
- 2019-3-26WinForm窗体间如何传值的几种方法
窗体间传递数据,无论是父窗体操作子窗体,还是子窗体操作符窗体,有以下几种方式: 公共静态变量: 使用共有属性: 使用委托与事件: 通过构造函数把主窗体传递到从窗体中: 一.通过静态变量 特点:传值是双 ...
- sql基本语法
sql基本语法 sql server 查询 多表查询 直接多表查询 select * from st_profiles,st_score_report 上面的语句将会产生两个表的笛卡尔乘积,其中大部分 ...
- tensorflow 使用 5 mnist 数据集, softmax 函数
用于分类 softmax 函数 手写数据识别:
- DEDECMS织梦文章摘要批量更改方法
我们建站有时候需要直接把数据库导入,只要修改一下基本的名称信息就可以直接用,但是遇用到一些问题.比如文章摘要不会随着文章内容的更新而更新.织梦(dede)在添加文章的时候会自动生成文章摘要,如果重新修 ...
- nginx配置前端代理
#user nobody;worker_processes 1; #error_log logs/error.log;#error_log logs/error.log notice;#error_l ...