Advertisement

【人人都能读标准】1. 标准的阅读指南

阅读量:

本文属于《人人都能读标准》ECMAScript系列中的第二篇文章。
我在此仓库中详细讲解了标准的基本规则及其应用方法,并对JavaScript的核心理论进行了深入分析。

打开ECMAScript2023,你将看到下图的这个界面,这就是我们通向卓越工程师的入口:

spec-interface

在该界面布局中左边区域包含一个标准目录结构以及一个基于标准设计的检索框右侧则提供了一个标准文本编辑界面

在初次接触标准时你可能会感到困惑不知该如何着手也找不到提升阅读速度的方法就像在一个广袤无垠的空间里迷路一样

这个过程可能会让你感到迷茫不知所措找不到一条清晰的学习路径就像在一个陌生的地方没有地图一样

缺乏明确的目标和方法会导致你在阅读中容易迷失方向如同在一个陌生环境里徒手 navigating without any guidance

在本节中, 我将为你提供一张"大纲"来帮助你理解核心内容, 并明确指向本书中的各个相关章节。随后, 我将分享一些基于实践经验的标准建议, 希望能提升你的阅读效率。

标准概览

总体而言,在ES语言规范中涵盖了以下四个核心要素:语法规则、运算规则以及运行时环境等关键部分,并提供了丰富的内置库以实现各种功能。

标准目前一共有29个章节,整体的内容架构如下表所示:

章节 内容
第1~4章 介绍标准。
第5章 定义整个标准使用的表示法约定。
第6~10章 定义执行环境的各个部分。
第11~17章 定义语言的文法和语义。
第18~28章 定义了语言的标准库。
第29章 定义了与sharedArrayBuffer相关的内存模型。
附录 补充内容。

第1~4章:介绍

前四章主要介绍了相关内容。其中涉及了ECMAScript其发展历程及其核心特性等基本概念。

我在介绍篇对这些介绍性内容作了许多有意义的扩展。

2.标准的迭代部分中,我通过一个具体实例向您演示标准是如何进行迭代的,并在此基础上归纳出标准的发展历程。

在GitHub仓库中的第3章《宿主环境》一节中,我通过多个实例向您展示了JavaScript如何与外部环境(例如浏览器和Node.js等)协同工作。通过这些实例分析,我们可以清楚地识别出属于ECMAScript规范定义的范围,以及另一些则遵循其他相关规范的规定。

第5章:表示法约定

在前言中,我使用了一个更加通熟易懂的词 —— 符号系统,来指代表示法约定(Notational Conventions) 。表示法约定主要分为两大部分:

它们是读懂标准的基础,也是把大多数人拒之门外的障碍。

在第4章‘文法基础’中,《 everyone-can-read-spec》详细阐述了文法表示方法;第6章‘算法’中,《 everyone-can-read-spec》详细介绍了算法表示方法

第6~10章:执行环境

执行环境是程序运行的基础,它由以下几个模块组成:

  • 支持的操作:包括该语言定义中所定义的所有数据类型的赋值运算符(Assignment operators)以及运算符重载机制(Operator overriding mechanism);
    • 常见的算法:涉及广泛使用的抽象操作(Abstract operations)以及遵循特定语法导向的操作(Syntax-directed operations);
    • 可用资源:包括agents(代理)、执行上下文(Execution context)、Realms( realm)以及作用域(Scope)等核心组件;

语言类型是我们熟悉的JavaScript中的八种数据类型,并可划分为标准定义的原始数据类型与标准定义的对象数据类型。在12. 原始数据类型一文中介绍了标准定义的原始数据类型的详细说明;而在13. 对象数据类型中则对标准定义的对象数据类型的实现进行了深入解析。规范类型的使用可能较为陌生,则是标准内部算法所依赖的一种特殊的数据形式;这一内容将在7. 规范型章节中进行详细介绍;

在整本书的不同位置上,《常用算法》的相关内容被分散地呈现。这是因为传统的'only algorithm'教学方式往往会让学习者感到乏味的原因,在遇到具体适用场景时我才会把必要的算法搬出来进行详细讲解。

可供使用的资源是高度重要的,并且具有一定的复杂性。具体包括8.执行环境、9.作用域以及10.作用域链这三个部分进行深入阐述这部分内容。

第11~17章:文法和语义

文法用来定义语言的合法结构,主要可以分为两类:词法文法与句法文法。

在第12章中,ECMAScript词法规则得到了标准的明确定义;从第13章开始一直到第16章这一段落中,则对ECMAScript的句法规则进行了详细阐述,并具体涵盖了以下内容:表达式、语句与声明、函数与类,以及脚本与模块。

我参考了该存储库中的文档,并详细阐述了这些语法规则及其在语义分析阶段的作用。此外还提供了一个系统性的综述框架。

在标准文法定义中形成的文法语义——语法导向操作

第18~28章:标准库

标准库亦即ECMAScript的内置对象之一。它是指那些预先配置好的的对象,在程序运行时直接可供使用,并涉及诸如全局对象与内置构造器等其他类型

标准库的主要部分与内置构造体具有关联。而对内置构造体的规定是被遵循一定的模板模式。举例来说,在命名一个叫做Example的对象时,则该对象将按照以下几点进行规范:

  1. 构造器的基本信息以及构造函数的具体逻辑:标题通常标注为「The Constructor's Core Information and Function Implementation」;
  2. 构造器的静态属性:通常以「Static Attributes of the Constructor」作为标题;
  3. 构造器的prototype对象属性:其对应的索引页应命名为「Prototype Object Attributes」;
  4. 构造器的实例属性:该部分通常以「Instance Properties」命名。

比如,下图是Number构造器的目录:

number-example

基础库并非我们重点关注的内容。作为一个官方指南( official guide ),本书的主要目标并不是对基础库进行详尽介绍。此外,在内容深度上它相对较为浅显。

标准库的一些内容更多地会在应用篇相关章节中被提及:

附录

附录主要是标准的补充内容,在这里,值得关注的地方有:

  • 附录A:文法的汇总;
  • 附录C:严格模式规则的汇总;
  • 附录D:宿主定义的汇总。

一些阅读标准的建议

把标准下载到本地阅读

请尝试访问标准的单页面版,然后在开发者工具中键入以下代码块:

复制代码
    console.log(document.body.textContent.length)
    console.log(document.body.getElementsByTagName('*').length)

这里的第一行代码用于统计网页内容的字符数量;统计结果显示该网页内容共有约210万字符。第二行代码用于统计网页中的HTML元素数量;统计结果显示该网页包含大约17,000个HTML元素。

不过,在单页版中访问开发者工具时所感受到的延迟感是我实际想要体验的东西;即使你没有打开开发者工具,在访问页面时标签也会耗时很久。

  1. 使用标准的PDF版本:我很快放弃了这一方案。因为标准页面所附带的交叉索引功能不可用,在此之后你会发现这一功能对于深入理解标准至关重要。
  2. 使用多页模式:多页模式将标准按照章节分拆成独立页面,在很大程度上改善了加载速度问题;在此书中所有引用的标准地方都是采用多页版本链接以确保读者能够快速定位到相关标准的位置。但这一模式存在一个显著的问题:由于对页面进行了分割处理,在无法直接利用浏览器提供的"全标准"检索框来进行精确搜索。
  3. 将标准下载至本地阅读:这是最佳选择方案。一方面它具备与多页模式相当甚至更好的加载速度;另一方面它又支持全标准检索功能无需依赖网络连接即可使用无需进行科学上网操作你在高铁车厢或飞机座位上都能随时打开它开始阅读。

你可从标准仓库中可获取到标准文档,并遵循指导实现本地化阅读体验。

刻意钻研新的概念

当遵循阅读标准时

  1. 该概念的核心内容是什么?
  2. 该方法是否与我已掌握的某一方法相类似?
    • 如果是的话,则二者有何不同之处?为使原有方法更加完善或适用性增强,则需对其作出何种调整?这种修改可能会影响到哪些相关联的概念或理论?在此基础上还需对哪些方面进行进一步优化?
    • 如果不是,则需探讨该新方法如何能够融入现有的认知体系中而不引起矛盾或冲突?

比如,在初次接触“Environment Record”的时候(或者说是当你第一次看到这个词的时候),你会觉得它与你 previously understood '作用域'有诸多相似之处(或者说这个概念与你所认知的作用域存在诸多共通点)。最初接触'作用域'的过程(或者说最初学习'作用域'的方法),你需要阅读大量的技术文献(或者说是相关技术文章)。这些文献各有优劣(无论是质量还是深度上),但这并不影响你对'作用域'的理解是否正确(或者说这些文献并不会影响到你对于标准描述的Environment Record的认知)。因此,在不断对比的过程中(或者说持续验证的过程中),你需要不断地审视自己对于"作用域"的理解,并做出必要的修正(或者说这种对比过程实际上也是一种自我校正机制)。这种持续的校正是会影响到其他相关概念的认识(比如说是作用域链、this值等),如果不对此进行相应的调整(或者说不对此进行相应的修正),那么你的知识体系就无法达到自洽的状态。

阅读标准即是为js概念库进行一次系统优化的过程。持续地将大脑中的混乱或冗余的认知替换为清晰且必要的信息,并在这一过程中逐步构建起各知识点间的关联网络。Issues of the learning standard is to achieve a comprehensive understanding of the JavaScript concepts.

该书的主要目标在于协助您提前建立核心概念。你可以访问前言中的词汇表一栏专门汇总了主要的概念框架。

善用交叉索引

「交叉索引」是理解标准的一大利器。

execution-context-example

交叉引用系统,在查看标准文本内容时,请您双击鼠标右键选择某一项的关键词语。该系统会呈现该术语在标准文档中的所有引用位置(如图所示)。

于是乎,在这种情况下

反过来说,在阅读一段文字内容时

交叉索引还有一个主要功能是帮助构建完整的知识架构。例如,在前言部分举了执行上下文的例子,并指出创建执行上下文的方式远远超出大家通常认为的三种情况;这一发现正是我在交叉索引中所获得的重要见解(如上图所示)。

读不懂就先跳过

在面对复杂书籍时遇到困难时不必要急于深入理解而应考虑"跳过"这一行为较之"切勿仓促放弃前一页"更为合理的选择

由于存在「前置引用」的现象,在学习过程中可能会遇到理解上的障碍。这种现象意味着一个在书后才被正式定义的概念,在学习过程中会被提前运用和参考。

比如如该标准第五章关于算法表示的部分,在第六章才定义了"完成记录器"这一概念之前就被提及了。并非因为编排存在缺陷,在构建系统时无法避免地会遇到这种前置引用的情况

因此,想要“平推式”地阅读标准,几乎是一个不可能完成的任务。

我们都有过这样的体会:某个 previously 不太明白的概念,在经过一段时间的潜移默化之后,在某个 day 突然间就通透起来。这种"顿悟"现象的发生原因,在本质上都是因为一个人想要真正 grasp 某个事情所需的所有 fundamental 的基础知识,在某段时间内有意或无意地全部都具备了。所谓"初听不知曲中意、再听已是曲中人"的说法,在某种程度上也是这样的情形啊!

这就是我们应当采取的重要原因。然而,在这一策略中必须注意的核心要点是"先"这一关键点。它表明未来还有机会重新阅读,并非仅仅一次地进行阅读——而是经过多次研读直至达到'曲中人'的程度。

输出倒逼输入

例证采用该策略作为典型方案。这本专著与另一本即将重构为《人人都能读标准2 —— HTML篇》的开源仓库可作为最佳参考材料。

我深刻认识到"产出"所带来的价值有多少;若未采取行动,则可能遭受多大的损失;两者之间的差异之大足以时常令人战栗的程度。

在输出的过程中, 为了清晰传达你的内容, 你会设定更高的表达标准. 经常会有这样的感悟: 原本以为非常熟悉的领域, 在深入理解时才发现其肤浅. 为了全面覆盖内容所需的知识储备, 则不得不深入学习那些平时看似不相关的知识. 为了更生动地呈现内容, 则需从不同角度深入探讨同一主题. 并从中筛选出最具代表性的实例进行详细阐述. 这一过程无疑能显著提升知识体系的广度和深度.

除此之外,在编写代码时除了撰写文章之外的内容外,你还可以参考标准的手写算法来实现类似的功能。例如,在深入理解 Promise 的基础上, 我根据 Promise 的定义手写了满足 test262 测试要求的一个 Promise 实例, 并提供了相应的代码链接: Promise

反正吧,“以教带学”这件事情,只要试过一次就戒不掉了。

认真阅读这本书

最后,容我王婆卖瓜一下:认真阅读这本书 —— 是最真诚、也是最有用的建议😊。

全部评论 (0)

还没有任何评论哟~