位置: 编程技术 - 正文

理解JS事件循环(js事件循环过程)

编辑:rootadmin

推荐整理分享理解JS事件循环(js事件循环过程),希望有所帮助,仅作参考,欢迎阅读内容。

文章相关热门搜索词:js事件循环机制的运用,nodejs事件循环和js事件循环,js事件循环执行顺序,js事件循环面试题,js事件循环执行顺序,js事件循环和任务队列,js事件循环面试题,js中事件循环的理解,内容如对您有帮助,希望把文章链接给更多的朋友!

伴随着JavaScript这种web浏览器脚本语言的普及,对它的事件驱动交互模型,以及它与Ruby、Python和Java中常见的请求-响应模型的区别有一个基本了解,对您是有益的。在这篇文章中,我将解释一些JavaScript并发模型的核心概念,包括其事件循环和消息队列,希望能够提升你对一种语言的理解,这种语言你可能已经在使用但也许并不完全理解。

这篇文章是写给谁的&#;

这篇文章是针对在客户端或服务器端使用或计划使用JavaScript的web开发人员的。如果你已经精通事件循环,那么这篇文章的大部分对你来说会很熟悉。对于那些还不是很精通的人,我希望能给你提供一个基本的了解,这样可以更好地帮助你阅读和编写日常代码。

非阻塞I / O

在JavaScript中,几乎所有的I/O都是非阻塞的。这包括HTTP请求,数据库操作和磁盘读写,单线程执行要求在运行期执行一个操作时,提供一个回调函数,然后继续做其它的事情。当操作已经完成时,消息和已提供的回调函数一起插入到队列。在将来的某个时候,消息从队列移除,回调函数触发。

虽然这种交互模型可能对已经习惯使用用户界面的开发人员很熟悉,比如“mousedown,”和“click”事件在某一时刻被触发。这与通常在服务器端应用程序进行的同步式请求-响应模型是不同的。

让我们来比较一下两小块代码,发出HTTP请求到www.google.com和输出响应到控制台。首先看看Ruby,配合使用Faraday(一个Ruby 的HTTP 客户端开发库):

执行路径很容易跟踪:

1、执行get方法,执行的线程等待,直到收到响应2、从谷歌收到响应并返回给调用者,它存储在一个变量中3、变量的值(在本例中,就是我们的响应)输出到控制台4、值“Done!“输出到控制台让我们使用Node.js和Request库在JavaScript做同样的事情:

表面上看略有不同,实际行为截然不同:

1、执行请求函数,传递一个匿名函数作为回调,当响应在将来某个时候可用时执行回调。2、“Done!“立即输出到控制台3、在将来的某个时候,响应返回和回调执行时,输出它的内容到控制台事件循环

将调用者和响应解耦,使得JavaScript在运行期等待异步操作完成和回调触发时可以做其他事情。但是这些回调在内存中是如何组织的,按什么顺序执行?什么导致他们被调用?

JavaScript运行时包含一个消息队列,它存储了需要处理的消息的列表和相关的回调函数。这些消息是以队列的形式来响应回调函数所涉及的外部事件(如鼠标单击或收到HTTP请求的响应)的。例如,如果用户单击一个按钮,但没有提供回调函数,那么也没有消息会被加入队列。

在一次循环,队列提取下一条消息(每次提取称为一次“tick”),当事件发生,该消息的回调执行。

理解JS事件循环(js事件循环过程)

回调函数的调用在调用栈作为初始化frame(片段),由于JavaScript是单线程的,未来的消息提取和处理因为等待栈的所有调用返回而被停止。后续(同步)函数调用会添加新的调用frame到栈(例如,函数init调用函数changeColor)。

在这个例子中,当用户单击“foo”元素时,一条消息(及其回调函数changeColor)会被插入到队列,并触发“onclick“事件。当消息离开队列时,其回调函数changeColor被调用。当changeColor返回(或者是抛出一个错误),事件循环仍在继续。只要函数changeColor存在,并指定为“foo”元素的onclick方法的回调,那么在该元素上单击会导致更多的消息(和相关的回调changeColor)插入队列。

队列附加消息

如果一个函数在代码中按异步调用(比如setTimeout),提供的回调将最终作为一个不同的消息队列的一部分被执行,它将发生在事件循环的某个未来的动作上。例如:

由于setTimeout的非阻塞特性,它的回调将在至少0毫秒后触发,而不是作为消息的一部分被处理。在这个示例中,setTimeout被调用, 传入了一个回调函数g且延时0毫秒后执行。当我们指定时间到达(当前情况是,几乎立即执行),一个单独的消息将被加入队列(g作为回调函数)。控制台打印的结果会是像这样:“foo”,“baz”,“blix”,然后是事件循环的下一个动作:“bar”。如果在同一个调用片段中,两个调用都设置为setTimeout -传递给第二个参数的值也相同-则它们的回调将按照调用顺序插入队列。

Web Workers

使用Web Workers允许您能够将一项费时的操作在一个单独的线程中执行,从而可以释放主线程去做别的事情。worker(工作线程)包括一个独立的消息队列,事件循 环,内存空间独立于实例化它的原始线程。worker和主线程之间的通信通过消息传递,看起来很像我们往常常见的传统事件代码示例。

首先,我们的worker:

然后,主要的代码块在我们的HTML中以script-标签存在:

在这个例子中,主线程创建一个worker,同时注册logResult回调函数到其“消息”事件。在worker里,reportResult函数注册到自己的“消息”事件中。当worker线程接收到主线程的消息,worker入队一条消息同时带上reportResult回调函数。消息出队时,一条新消息发送回主线程,新消息入队主线程队列(带上logResult回调函数)。这样,开发人员可以将cpu密集型操作委托给一个单独的线程,使主线程解放出来继续处理消息和事件。

关于闭包的

JavaScript对闭包的支持,允许你这样注册回调函数,当回调函数执行时,保持了对他们被创建的环境的访问(即使回调的执行时创建了一个全新的调用栈)。理解我们的回调作为一个不同的消息的一部分被执行,而不是创建它的那个会很有意思。看看下面的例子:

在这个例子中,changeHeaderDeferred函数被执行时包含了变量header。函数 setTimeout被调用,导致消息(带上changeHeader回调)被添加到消息队列,在大约毫秒后执行。然后 changeHeaderDeferred函数返回false,结束第一个消息的处理,但header变量仍然可以通过闭包被引用,而不是被垃圾回收。当 第二个消息被处理(changeHeader函数),它保持了对在外部函数作用域中声明的header变量的访问。一旦第二个消息 (changeHeader函数)执行结束,header变量可以被垃圾回收。

提醒

JavaScript 事件驱动的交互模型不同于许多程序员习惯的请求-响应模型,但如你所见,它并不复杂。使用简单的消息队列和事件循环,JavaScript使得开发人员在构建他们的系统时使用大量asynchronously-fired(异步-触发)回调函数,让运行时环境能在等待外部事件触发的同时处理并发操作。然而,这不过是并发的一种方法。

标签: js事件循环过程

本文链接地址:https://www.jiuchutong.com/biancheng/384741.html 转载请保留说明!

上一篇:JavaScript中定义类的方式详解(JavaScript中定义数组)

下一篇:JavaScript中的原始值和复杂值(js原型作用)

  • 应税销售收入是指什么
  • 账面价值大于计税基础是什么差异
  • 国有划拔土地房整体可以买卖吗
  • 销售收入与营业费用的配比
  • 要补交税怎么办
  • 出口退税综合服务平台广东
  • 收到红字专票怎么做账务处理
  • 实收资本能是现金流出吗
  • 从业人数和资产总额是灰色
  • 集团公司内部调动
  • 债务重组的会计处理方法
  • 企业实际发生的公益性捐赠支出
  • 不能抵扣的普通发票
  • 工厂报废的产品价格有规定吗
  • 刻章发票可以抵税吗
  • 超市购物卡开票可以做账吗
  • 个人汽车租给公司租金需多少钱?
  • 滞纳金是否有上限
  • 企业卖固定资产
  • 转口贸易是否缴增值税
  • 实收资本的会计处理
  • 会计准则规定
  • 房产免租期间缴纳房产税吗
  • 出口免税金额
  • linux dns配置服务器
  • 对公汇款银行退回
  • 小公司做帐
  • win7安装驱动程序
  • 来电转接怎么设置空号
  • win10如何关闭更新并关机
  • 向境外股东分配利润代扣代缴企业所得税
  • 营业利润是怎么计算的?
  • 深度学习中模型计算量(FLOPs)和参数量(Params)的理解以及四种计算方法总结
  • PHP中使用什么关键字声明变量的作用域为全局
  • 广告费与业务宣传费扣除给企业带来的好处
  • 地下停车位是否符合国家安全标准咨询那个部门
  • 计算机视觉会议2023年11月
  • php设置图片将图片居中
  • 独立核算的基金是会计主体吗
  • php获取服务器ip和客户端ip的方法
  • 会计分录结转进项怎么算
  • 固定资产到期后残值怎么处理
  • 银行贷款入账需要什么
  • 对公银行卡账户
  • 税盘抵扣怎么做分录
  • 下列项目的进项税额可以从销售税额中抵扣的是
  • 发票上没有数量可以吗
  • sql server 2008使用
  • 应收账款贷方如何核算
  • 决算清理期和库款报解整理期
  • 新开立银行账户怎么办理
  • 开出银行承兑汇票一张用于支付材料采购款
  • 资本公积的相关资料
  • 车辆不在公司名下加油费可以进公司吗
  • 可以自行开具增值税专用发票的行业有哪些
  • 招待费汇算清缴一定要调整的吗
  • 进项税额转出在哪里查
  • 债权人接受债务怎么处理
  • mysql详细介绍
  • MySQL数据库备份
  • mysql 5.6.14 win32 解压缩版(免安装)安装配置教程
  • windows录音机录音文件格式
  • 下载微信
  • 64位win10预览版10565更新补丁KB3105208后蓝屏怎么办?
  • ubuntu 上不了网
  • windows8安装itunes
  • 安装linux系统步骤图解
  • linux限制用户cpu使用
  • android viewpager
  • 关于android中view的说法正确的是
  • android源码分析实录
  • javascript高级程序设计电子书
  • 关于javascript函数
  • cocos引擎教程
  • js实现字符串和数字对齐
  • flash谈广告
  • 306医院改名什么了
  • 盐城企退人员养老金调整新标准
  • 小规模纳税人租赁房屋税率
  • 出口货物免抵税额怎么申报附加税
  • 免责声明:网站部分图片文字素材来源于网络,如有侵权,请及时告知,我们会第一时间删除,谢谢! 邮箱:opceo@qq.com

    鄂ICP备2023003026号

    网站地图: 企业信息 工商信息 财税知识 网络常识 编程技术

    友情链接: 武汉网站建设