1- # 函数原型
1+ # F.prototype
22
3- 正如我们已经知道的那样, ` new F() ` 创建一个新对象 。
3+ 我们还记得,可以使用诸如 ` new F() ` 这样的构造函数来创建一个新对象 。
44
5- 当用 ` new F() ` 创建一个新对象时,该对象的 ` [[Prototype]] ` 被设置为 ` F.prototype ` 。
5+ 如果 ` F.prototype ` 是一个对象,那么 ` new ` 操作符会使用它为新对象设置 ` [[Prototype]] ` 。
66
77``` smart
8- JavaScript 从一开始就有了原型继承。这是该语言的核心特征之一 。
8+ JavaScript 从一开始就有了原型继承。这是 JavaScript 编程语言的核心特性之一 。
99
10- 但在过去,我们是无法直接对其进行访问的。唯一可靠的设置方法是使用构造函数的“ prototype” 属性。我们将在本章对其进行讨论。即使现在,还是有很多使用它的脚本 。
10+ 但是在过去,没有直接对其进行访问的方式。唯一可靠的方法是本章中会介绍的构造函数的 `" prototype"` 属性。目前仍有许多脚本仍在使用它 。
1111```
1212
13- 请注意,` F.prototype ` 意味着在 ` F ` 上有一个名为 ` "prototype" ` 的常规属性。这听起来与“原型”这个术语很相似,但在这里我们的意思是指有这个名字的常规属性 。
13+ 请注意,这里的 ` F.prototype ` 指的是 ` F ` 的一个名为 ` "prototype" ` 的常规属性。这听起来与“原型”这个术语很类似,但这里我们实际上指的是具有该名字的常规属性 。
1414
15- 这是一个例子 :
15+ 下面是一个例子 :
1616
1717``` js run
1818let animal = {
@@ -32,25 +32,25 @@ let rabbit = new Rabbit("White Rabbit"); // rabbit.__proto__ == animal
3232alert ( rabbit .eats ); // true
3333```
3434
35- 设置 ` Rabbit.prototype = animal ` 的这段代码表达的意思是:“当 ` new Rabbit ` 创建时 ,把它的 ` [[Prototype]] ` 赋值为 ` animal ` ” 。
35+ 设置 ` Rabbit.prototype = animal ` 的字面意思是:“当创建了一个 ` new Rabbit ` 时 ,把它的 ` [[Prototype]] ` 赋值为 ` animal ` ”。
3636
37- 这是结果图 :
37+ 这是结果示意图 :
3838
3939![ ] ( proto-constructor-animal-rabbit.svg )
4040
41- 在图片上 ,` "prototype" ` 是一个水平箭头,它是一个常规属性 ,` [[Prototype]] ` 是垂直的,意味着是继承自 ` animal ` 的 ` rabbit ` 。
41+ 在上图中 ,` "prototype" ` 是一个水平箭头,表示一个常规属性 ,` [[Prototype]] ` 是垂直的,表示 ` rabbit ` 继承自 ` animal ` 。
4242
43- ```smart header="` F.prototype ` 仅用于 ` new F ` 时"
44- ` F.prototype ` 属性仅在 ` new F ` 调用时使用 ,它为新对象的 ` [[Prototype]] ` 赋值。在此之后 ,` F.prototype ` 和新对象之间就分道扬镳了。可以将其看为一个“单次赠与”效果 。
43+ ```smart header="` F.prototype ` 仅用在 ` new F ` 时"
44+ ` F.prototype ` 属性仅在 ` new F ` 被调用时使用 ,它为新对象的 ` [[Prototype]] ` 赋值。之后 ,` F.prototype ` 和新对象之间就没有任何联系了。可以把它看成“一次性的礼物” 。
4545
46- 如果在创建之后 ` F.prototype ` 属性有了变化( ` F.prototype = <another object> ` ),那么 ` new F ` 创建的新对象也将随之拥有新的 ` [[Prototype]] ` 。 但已经存在的对象将保持旧有的值。
46+ 如果在创建之后, ` F.prototype ` 属性有了变化( ` F.prototype = <another object> ` ),那么通过 ` new F ` 创建的新对象也将随之拥有新的对象作为 ` [[Prototype]] ` , 但已经存在的对象将保持旧有的值。
4747```
4848
49- ## 默认的函数原型 ,构造函数属性
49+ ## 默认的 F.prototype ,构造函数属性
5050
51- 每个函数都有 `"prototype"` 属性,即使我们不设置它 。
51+ 每个函数都有 `"prototype"` 属性,即使我们没有提供它 。
5252
53- 默认的 `"prototype"` 是一个只有属性 `constructor` 的对象,它指向函数本身 。
53+ 默认的 `"prototype"` 是一个只有属性 `constructor` 的对象,属性 `constructor` 指向函数自身 。
5454
5555像这样:
5656
@@ -74,7 +74,7 @@ function Rabbit() {}
7474alert ( Rabbit .prototype .constructor == Rabbit ); // true
7575```
7676
77- 当然 ,如果我们什么都不做,` constructor ` 属性可以通过 ` [[Prototype]] ` 给所有 rabbits 对象使用 :
77+ 通常 ,如果我们什么都不做,` constructor ` 属性可以通过 ` [[Prototype]] ` 给所有 rabbits 使用 :
7878
7979``` js run
8080function Rabbit () {}
@@ -88,9 +88,10 @@ alert(rabbit.constructor == Rabbit); // true (from prototype)
8888
8989![ ] ( rabbit-prototype-constructor.svg )
9090
91- 我们可以用 ` constructor ` 属性使用与现有构造函数相同的构造函数创建一个新对象 。
91+ 我们可以使用 ` constructor ` 属性来创建一个新对象,该对象使用与现有对象相同的构造函数 。
9292
9393像这样:
94+
9495``` js run
9596function Rabbit (name ) {
9697 this .name = name;
@@ -104,16 +105,15 @@ let rabbit2 = new rabbit.constructor("Black Rabbit");
104105*/ ! *
105106```
106107
107- 当我们有一个对象,但不知道为它使用哪个构造函数(比如它来自第三方库),而且我们需要创建另一个相似的函数时,用这种方法就很方便。
108-
108+ 当我们有一个对象,但不知道它使用了哪个构造函数(例如它来自第三方库),并且我们需要创建另一个类似的对象时,用这种方法就很方便。
109109
110- 但关于 ` "constructor" ` 最重要的是......
110+ 但是,关于 ` "constructor" ` 最重要的是……
111111
112- ** ... JavaScript 本身并不能确保正确的 ` "constructor" ` 函数值。**
112+ ** …… JavaScript 自身并不能确保正确的 ` "constructor" ` 函数值。**
113113
114- 是的,它存在于函数的默认 ` "prototype" ` 中,但仅此而已。之后会发生什么 —— 完全取决于我们自己 。
114+ 是的,它存在于函数的默认 ` "prototype" ` 中,但仅此而已。之后会发生什么 —— 完全取决于我们 。
115115
116- 特别是,如果我们将整个默认原型替换掉,那么其中就不会有构造函数 。
116+ 特别是,如果我们将整个默认 prototype 替换掉,那么其中就不会有 ` "constructor" ` 了 。
117117
118118例如:
119119
@@ -129,15 +129,15 @@ alert(rabbit.constructor === Rabbit); // false
129129*/ ! *
130130```
131131
132- 因此,为了确保正确的 ` "constructor" ` ,我们可以选择添加/删除属性到默认 ` "prototype" ` 而不是将其整个覆盖:
132+ 因此,为了确保正确的 ` "constructor" ` ,我们可以选择添加/删除属性到默认 ` "prototype" ` , 而不是将其整个覆盖:
133133
134134``` js
135135function Rabbit () {}
136136
137- // Not overwrite Rabbit.prototype totally
138- // just add to it
137+ // 不要将 Rabbit.prototype 整个覆盖
138+ // 可以向其中添加内容
139139Rabbit .prototype .jumps = true
140- // the default Rabbit.prototype.constructor is preserved
140+ // 默认的 Rabbit.prototype.constructor 被保留了下来
141141```
142142
143143或者,也可以手动重新创建 ` constructor ` 属性:
@@ -156,20 +156,20 @@ Rabbit.prototype = {
156156
157157## 总结
158158
159- 在本章中,我们简要介绍了如何为通过构造函数创建的对象设置一个 `[[Prototype]]`。稍后我们将看到更多依赖于它的高级编程模式 。
159+ 在本章中,我们简要介绍了为通过构造函数创建的对象设置 `[[Prototype]]` 的方法。稍后我们将看到更多依赖于此的高级编程模式 。
160160
161- 一切都很简单,只需要几条笔记就能说清楚 :
161+ 一切都很简单,只需要记住几条重点就可以清晰地掌握了 :
162162
163- - `F.prototype` 属性与 `[[Prototype]]` 不同。`F.prototype` 唯一的作用是:当 `new F ()` 被调用时,它设置新对象的 `[[Prototype]]`。
164- - `F.prototype` 的值应该是一个对象或 null:其他值将不起作用 。
165- - `"prototype"` 属性在设置为构造函数时仅具有这种特殊效果,并且用 `new` 调用 。
163+ - `F.prototype` 属性(不要把它与 `[[Prototype]]` 弄混了)在 `new F` 被调用时为新对象的 `[[Prototype]]` 赋值 。
164+ - `F.prototype` 的值要么是一个对象,要么就是 ` null`:其他值都不起作用 。
165+ - `"prototype"` 属性仅在设置了一个构造函数( constructor function ),并通过 `new` 调用时,才具有这种特殊的影响 。
166166
167167在常规对象上,`prototype` 没什么特别的:
168168```js
169169let user = {
170170 name: "John",
171- prototype: " Bla-bla" // 没什么神秘的
171+ prototype: "Bla-bla" // 这里没有魔法了
172172};
173173```
174174
175- 默认情况下,所有函数都有 ` F .prototype = {constructor :F}`,所以我们可以通过访问它的 `"constructor "` 属性来获得对象的构造函数 。
175+ 默认情况下,所有函数都有 `F.prototype = {constructor :F}`,所以我们可以通过访问它的 `"constructor "` 属性来获取一个对象的构造函数 。
0 commit comments