Javascript: The Good Parts 笔记

0. JS的组成部分

  • 核心(ECMAScript): 核心语言功能.
  • 文档对象模型(DOM): 访问和操作网页内容的方法和接口.
  • 浏览器对象模型(BOM): 与浏览器交互的方法和接口.

1. 语法

  • / * */ 注释块是不安全的.
    • 由于/*也会出现在正在表达式的字面量中, 所以是不安全的.
    • 尽量使用//来代替/*.
  • 数字类型
    • 只有一种数字类型, 在内部被表示为64位的浮点数.
    • 并未分离出证书类型. 所以 1 === 1.0
    • e�代表指数部分:` 100 === 1e2.
  • 字符串
    • 没有char 类型.
    • \u 用来指定数字字符编码
      • 'A' === '\u0041'.

2. 对象

  • 对象是可悲的键控集合( keyed collections).
    • 数字,函数,正则表达式都是对象.
  • 在获取对象的成员的值时, 使用||来填充默认值.
    • var status = flight.status || 'unknown'.
  • 原型链
    • 原型连接只在检索时才被用到, 并且是动态的关系.
      • 添加新属性后, 立即对创建的对象可见.
    • 删除和更新属性都不会触及原型链, 而只会影响当前对象.
      • delete 可能会暴露出原本被覆盖掉的原型链上的属性.
    • 使用hasOwnProperty 来禁止原型链检查.
  • 减少全局变量污染
  • 创建一个唯一的全局变量, var myMap = {};
  • 然后以此变量作为应用的容器. 其它变量都是其属性.

3. 函数

  • 3.1 一个JS函数也是一个对象.
    • 所有的对象从技术上讲也只是函数.
    • 函数会连接到Function.prototype 原型上.
    • 函数创建时的隐藏属性:
      • 函数的上下文和实现函数行为的代码.
      • 一个”调用”属性(调用函数时,调用的是该属性).
    • 闭包: 连接到外部上下文的连接.
  • 3.2 函数的调用模式. 导致this参数的差异.
    • 方法调用模式.
      • 保存为对象属性的函数,称为方法.
      • 在方法被调用时,this被绑定到该对象上.
    • 函数调用模式.
      • 并非对象的属性的函数. this被绑定到了全局对象上.
      • 当函数作为内部函数时, 由于this为全局对象,所以必须使用闭包特性(定义一个外部变量值保存this)来在函数内部使用外部对象的属性.
    • 构造器调用模式.
      • 在函数调用时加上new. 将会创建一个连接到该函数的prototype成员的新对象. 且this被绑定到新对象上.
      • 构造器函数约定为以大写字母开头. 但是调用它时如果没有加new,不会有异常和警告发生,所以应替代之.
    • Apply调用模式.
      • 函数默认拥有apply(this,参数数组)方法.
  • 3.3 参数
    • 调用时,会生成一个arguments伪数组(用于length,但是没有其他数组方法),利用它实现可变参数特性.
  • 3.4 返回
    • 总是会有返回值,在未指定时,返回undefined. new调用时,返回this.
  • 3.5 异常
    • 一个try只能有一个catch,若要处理特定类型的异常,检查异常对象的name来确定其属性.
  • 3.6 扩充类型的功能.
    • 给Object/Function/Number.prototype添加方法.
    • 由于原型是公用结构,保险的做法是在没有该方法时才添加它.
  • 3.7 尾递归优化
    • 函数的末尾是返回自身递归调用的结果, 由于再创建新的调用栈纯属无用,会重用当前调用栈,而调用过程会成为一个循环调用.
    • JS没有进行尾递归优化, 所以深度递归的函数可能会栈溢出而失败.
  • 3.8 作用域
    • JS并没有块级作用域的概念,所以应该在函数的顶部声明所有的变量. JS只有函数作用域.
  • 3.9 闭包
    • 内部函数拥有比它的外部函数更长的生命周期.
    • 内部函数无需复制就能访问外部函数的实际变量.
  • 3.10 模块
    • 使用函数产生模块,来摒弃全局变量的使用.
    • 模块模式: 定义了私有变量和函数的函数; 利用闭包创建可以访问到两者的特权函数,最后返回该特权函数.
    • 可用来产生安全的对象,如用以产生序列号的对象.
  • 3.11 柯里化
    • 把多参函数转换为一系列单参数函数并调用的技术.
    • 把函数与传递给它的参数相结合,从而产生出新的函数.
  • 3.12 记忆
    • 将先前操作的结果记录在某对象里,从而避免无谓的重复计算. 使用数组+闭包来实现.
    • 设计产生另一函数的函数,来减少工作量.

4. 继承

  • JS是弱类型的,不需要类型转换.
    • **重要的是对象能做什么,而不是从哪里来. **
    • 对象可以直接从其他对象继承.
  • 对象从其它对象继承时的间接层: 通过构造器函数产生对象.

5. 数组

  • 类数组特征的对象,并非真正的数组.将下标作为属性使用.
    • 混合类型的元素, 元素可以为各种类型.
  • 长度. 不会越界,length为最大下标属性+1,而非元素个数.
    • 增大length不会分配更多空间,减少length会删除后续元素.
    • numbers[numbers.length]=2; 等同于: numbers.push(2).
  • 删除. 数组就是对象,使用delete删除元素时会留下空洞. 使用splice()来删除一些元素并替换为其它的元素.
  • 混淆. 当属性名是小而连续的整数时,使用数组,否则使用对象.
    • 判断对象是否为数组: function (value) { return Object.prototype.toString.apply(value) === ‘[object Array]’;}
  • 没有多维数组,自行创建元素为数组的数组.
  • array的方法
    • join, pop, reverse.
    • shift,(移出首元素),unshift(插到首位)
    • sort(将元素以字符串形式排序,排列数字时可传递自定义比较函数).

6. 正则表达式

  • 所有部分必须紧密排列在一起,不支持注释和空白.

7. 精简的JS

  • 函数是顶级对象. 函数是有词法作用域的闭包.
  • 基于原型继承的动态对象. 对象是无类别的.
  • 对象字面量和数组字面量. 列出对象的组成部分,就能创建出对象. JSON

8. JS 糟粕

  • 全局变量. 由于没有链接器,JS依赖于全局变量进行连接. 所有编译单元的顶级变量被撮合到全局对象的公共命名空间中.
    • 函数外的var声明; 全局对象(window)上添加的属性; 直接使用未经声明的变量(隐式的全局变量).
  • 作用域. 代码块({})不会创建新的作用域,所以变量应定义在函数头部.
    • js 中只有全局作用域和函数作用域, 而并没有局部作用域.
  • 容易导致错误的自动插入分号机制.
  • 含有大量语言并未使用的保留字.
  • 16位的Unicode. 会把(表示单个字符的)一对字符认为是两个不同的字符.
  • typeof 辨别不出null, 也区分不出数组和对象.
  • parseInt,会遇到非数字时停止(并返回之前解析出的数字). 首字符为0时按八进制求值,最好加上基数参数.
  • 浮点数, 二进制浮点数不能精确地处理十进制小数(0.1+0.2!=0.3). 通过将其转化为整数来避免该问题.
  • NaN.
    • typeof NaN = ‘number’, NaN !== NaN.使用isNaN.
    • 使用isFinite判断值是否可做数字, 而为了避免它的试图转换. 首先判断值的typeof是否为number.
  • 对象. 永远不会是真的空对象. 因为可从原型链中取得成员属性.
  • == 会试图去强制转换类型, 应始终使用===.
  • 避免使用with, 其原意是快捷地访问对象的属性.
  • function语句会被提升, 无论其在哪里定义,都会被移动到定义所在作用域的顶层,从而放宽了先定义后使用的要求.
    • 应避免使用function语句,而使用function表达式.
    • 避免: function foo(){} ==> 而使用: var foo = function foo(){}.
  • 避免使用类型的包装对象.
    • �例如: new Boolean, new Object, new Array, 应使用 {}, []代替.
  • void是运算符.
    • 接收一个运算数并返回undefined, 应避免使用它.
  • new 操作符: 基于该函数的原型创建一个新对象,
    • 在忘记使用new时带来风险(不会创建对象,且this 被绑定到全局对象上). 应避免使用new.
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 217,185评论 6 503
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,652评论 3 393
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 163,524评论 0 353
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 58,339评论 1 293
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 67,387评论 6 391
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 51,287评论 1 301
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 40,130评论 3 418
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,985评论 0 275
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,420评论 1 313
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,617评论 3 334
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,779评论 1 348
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,477评论 5 345
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 41,088评论 3 328
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,716评论 0 22
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,857评论 1 269
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,876评论 2 370
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,700评论 2 354

推荐阅读更多精彩内容