[Effective JavaScript 笔记]第7章:并发--个人总结
前言
这一章的内容学到了事件队列和异步的API。js只是运行在其他应用程序的脚本语言。js即依赖于应用程序,也独立与应用程序。可以使它可以在多平台,多种环境上运行。ECMAScript标准中没有关于并发的说明。这章讨论的是一些常用的方法,使用事件和异步API是js编程的基础部分。异步API,有setTimeout,setInterval。
第61条:不要阻塞I/O事件队列
个人总结
js是构建在事件之上的单线程语言。js处理交互都以事件的方法进行传递的,监听事件的处理函数,都根据事件队列的执行相应的监听函数。
同步处理
同步处理,在一个I/O请求中,会等待输入的内容。如果没有输入会一直等待下去,直到输入有结果。这个时候,在多线程的语言里可以开另一个线程处理其他计算,但js是单线程的语言,只能一直等,也就是阻塞了,浪费了计算机资源。
异步处理
在js中,可以为一个I/O操作提供一个回调函数,然后程序会继续处理下面的代码。直到I/O有输入时,回调函数才会执行相关操作。这是由事件队列的特性来实现的,这样就可以实现无阻塞的代码。
提示
异步API使用回调函数来延缓处理代价高昂的操作以避免阻塞主应用程序
js并发地接收事件,但会使用一个事件队列按序地处理事件处理程序
在应用程序事件队列中绝不要使用阻塞的I/O
第62条:在异步序列中使用嵌套或命名的回调函数
个人总结
理解操作序列的最简单的方式是异步API的发起操作而不是执行操作。所以在发起操作后的代码会先执行,而到后面的事件循环的轮次中,被注册的事件处理程序才会执行。串联已完成的异步操作,可以使用嵌套的方式来进行。但层次过多会导致代码很乱,很长。减少嵌套的方法:使用命名函数,使用bind方法来绑定。把这些方式结合在一起使用,可以更好解决问题。
提示
使用嵌套或命名的回调函数按顺序地执行多个异步操作
尝试在过多的嵌套的回调函数和尴尬的命名的非嵌套回调函数之间取得平衡
避免将可被并行执行的操作顺序化
第63条:当心丢弃错误
个人总结
管理异步编程,调试不太容易,错误发生的地方和错误捕获的地方不好定位。这里对异步操作把错误的信息的以回调函数参数的形式向外层传递。在回调函数中对错误进行处理,可以使代码可以正常运行。
提示
通过编写共享的错误处理函数来避免复制和粘贴错误处理代码
确保明确地处理所有的错误条件以避免丢弃错误
第64条:对异步循环使用递归
个人总结
异步循环,62条所说的一样,这里的循环只是同时发起了多个操作,但并不是执行操作。所以无法在执行操作中对循环进行中止。把循环的操作改写成函数的递归,把异步的发起和执行进行序列化。但又会有一个新的问题,js环境通常在内存中保存一块固定的区域,称为调用栈,用于记录函数调用返回前下一步该做什么。这是以栈的方式来存储的“先进后出”。但如果这样的调用次数过多,会导致栈空间被耗尽,最终会抛出异常,即栈溢出。
提示
循环不能是异步的
使用递归函数在事件循环的单独轮次中执行迭代
在事件循环的单独轮次中执行递归,并不会导致调用栈溢出
第65条:不要在计算时阻塞事件队列
个人总结
第61条解释了异步API如何防止一段程序阻塞应用程序的事件队列。如果是一段正常的执行代码一直占用线程,事件队列中的操作无法执行。这段时间里在浏览器环境中,无法响应
用户操作。Web客户端平台的Worker API,可以处理纯数据的计算,从而防止计算时对事件队列的阻塞。
提示
避免在主事件队列中执行代价高昂的算法
在支持Worker API的平台,该API可以用来在一个独立的事件队列中运行长计算程序
在Worker API不可用或代价昂贵的环境中,考虑将计算程序分解到事件循环的多个轮次中
第66条:使用计数器来执行并行操作
个人总结
当处理多个并发时,无法保重回调函数中参数的顺序。导致后期代码无法正确运行,对于每次发起操作记一次数,返回时对对应的返回结果进行记录。回调函数再对记录的结果进行处理。可以保证程序按预定步骤进行运行。
提示
js应用程序中的事件发生是不确定的,即顺序是不可预测的
使用计数器避免并行操作中的数据竞争
第67条:绝不要同步地调用异步的回调函数
个人总结
异步的返回结果,可以保存在一个缓存中。在这种情况下,再进行多文件同步下载,可以使用缓存中的数据,所以回调函数可以同步地执行。但就像64条上的调用栈有可能会出现问题,会导致栈空间耗尽。回调函数也使用异步调用,使用setTimeout来调用对应的回调函数。
提示
即使可以立即得到数据,也绝不要同步地调用异步回调函数
同步地调用异步的回调函数扰乱了预期的操作序列,并可能导致意想不到的交错代码
同步地调用异步的回调函数可能导致栈溢出或错误地处理异常
使用异步的API,比如setTimeout函数来调度异步回调函数,使其运行于另一回合
第68条:使用promise模式清洁异步逻辑
个人总结
使用promise模式,可以把多层嵌套函数,改写成一种同步传入回调函数的方式。这样可以利用各种工具函数对其进行处理。如then,when,join,select等。
提示
promise代表最终值,即并行操作完成时最终产生的结果
使用promise组合不同的并行操作
使用promise模式的API避免数据竞争
在要求有意的竞争条件时使用select(也被称为choose)
总结
异步调用,利用事件队列防止阻塞
函数的多次递归调用,调用栈可能会耗尽
纯计算,使用web客户端的Worker API
使用计数器,可以保证异步的结果顺序
使用处理异步调用的工具框架
可以防止数据竞争
[Effective JavaScript 笔记]第7章:并发--个人总结的更多相关文章
- [Effective JavaScript 笔记]第3章:使用函数--个人总结
前言 这一章把平时会用到,但不会深究的知识点,分开细化地讲解了.里面很多内容在高3等基础内容里,也有很多讲到.但由于本身书籍的篇幅较大,很容易忽视对应的小知识点.这章里的许多小提示都很有帮助,特别是在 ...
- [Effective JavaScript 笔记] 第1章:让自己习惯javascript小结
在这里整理一下,每条对应的提示 第1条:了解使用的js版本 确定应用程序支持的js的版本(浏览器也是应用程序噢) 确保使用的js特性是应用程序支持的(要不写了也运行不了) 总是在严格模式下编写和测试代 ...
- [Effective JavaScript 笔记]第2章:变量作用域--个人总结
前言 第二章主要讲解各种变量作用域,通过这章的学习,接触到了很多之前没有接触过的东西,比如不经常用到的eval,命名函数表达式,with语句块等,下面是一个列表,我对各节的一点点个人总结,很多都是自己 ...
- [Effective JavaScript 笔记]第4章:对象和原型--个人总结
前言 对象是js中的基本数据结构.对象在js语言编码中也随处可见,比如经常会用到的函数,也是一个Function构造函数,Function.prototype原型对象.每当声明一个函数时,都会继承Fu ...
- [Effective JavaScript 笔记]第5章:数组和字典--个人总结
前言 这节里其实一直都在讨论对象这个在js中的万能的数据结构.对象可以表式为多种的形式,表示为字典和数组之间的区别.更多的我觉得这章讨论多的是一些对应实现功能的相关操作,有可能出现的bug以及如何避免 ...
- [Effective JavaScript 笔记]第6章:库和API设计--个人总结
前言 又到了一章的总结,这章里的内容.是把我从一个代码的使用者,如何换位成一个代码的编写者.如何让别人用自己的代码更容易,不用去注意太多的无用细节,不用记住冗长的函数名.在使用API时怎样避免使用者会 ...
- [Effective JavaScript 笔记] 第4条:原始类型优于封闭对象
js有5种原始值类型:布尔值.数字.字符串.null和undefined. 用typeof检测一下: typeof true; //"boolean" typeof 2; //&q ...
- [Effective JavaScript 笔记] 第5条:避免对混合类型使用==运算符
“1.0e0”=={valueOf:function(){return true;}} 是值是多少? 这两个完全不同的值使用==运算符是相等的.为什么呢?请看<[Effective JavaSc ...
- [Effective JavaScript 笔记]第27条:使用闭包而不是字符串来封装代码
函数是一种将代码作为数据结构存储的便利方式,代码之后可以被执行.这使得富有表现力的高阶函数抽象如map和forEach成为可能.它也是js异步I/O方法的核心.与此同时,也可以将代码表示为字符串的形式 ...
随机推荐
- About-PHP-02
如果要给table里面的td添加颜色,有两种方法: <html> <head> <meta http-equiv="Content-Type" con ...
- js中return,this,arguments,currentStyle和getComputedStyle小析
一.return返回值:1.函数名+括号:fn()==>return 后面的值2.所有函数默认返回值:未定义3.return后面的任何代码都不会执行二.this:当前对象1.当某个对象后边加事件 ...
- 数据库之SQL语法
-- 创建数据库CREATE DATABASE mytest; -- 创建表CREATE TABLE t_user( -- primary key 定义该列为主键列 -- AUTO_INCREMENT ...
- java-两个大数相加
题目要求:用字符串模拟两个大数相加. 一.使用BigInteger类.BigDecimal类 public static void main(String[] args) { String a=&qu ...
- js控制只允许输入数字
avascript 只允许输入数字有很多方法,总结如下 1,只允许输入数字和小数点. <input onKeypress="return (/[\d.]/.test(String.fr ...
- Leetcode | Find Minimum in Rotated Sorted Array I && II
Suppose a sorted array is rotated at some pivot unknown to you beforehand. (i.e., 0 1 2 4 5 6 7 migh ...
- Debug阶段成员贡献分
组名:天天向上 组长:王森 组员:张政.张金生.林莉.胡丽娜 Debug阶段各组员的贡献分分配如下: 姓名 个人工作量 组长评价 个人评价 团队贡献总分 张金生 11 7 6 6.00 张政 11 6 ...
- windows下安装 sphinx 数据库全文搜索引擎
此次演示的环境是:win7系统,64位,php5.4.x,apache sphinx,斯芬克斯(英语不好的同学可以直接读这个音),意狮身人面像 特点:创建索引速度快,3分钟左右能创建100万条记录的索 ...
- oracle 用户锁定及到期
select * from dba_users where username='HR'--查询用户状态 alter user HR identified by HR;--重新更新密码alter use ...
- php的spl_autoload_register函数的一点个人见解
这是一篇对spl_autoload_register()函数的个人简单介绍,有需要的同学可以参考,主要是讨论spl_autoload_register()函数所注册的函数的参数的个人一点迷惑. 废话不 ...