原型与原型链的理解
在 JavaScript 中,每个对象都有一个“隐藏属性”指向另一个对象,这个对象就是它的原型,我们可以通过 __proto__
来访问它。
例如:
1 | const obj = { name: '小明' }; |
这表示 obj
是通过 Object
构造函数创建的,它的原型是 Object.prototype
。JavaScript 在访问对象的属性时,如果对象本身没有,就会从它的原型上找。
什么是原型链?
对象的 __proto__
属性(实际标准中叫 [[Prototype]]
)会一直向上指向另一个对象,直到指向 null
为止,这条向上查找的路径就叫做原型链。
例子:
1 | function Person() {} |
这里的查找过程是:
1 | p → p.__proto__(Person.prototype)→ Person.prototype.__proto__(Object.prototype)→ null |
只要找到为止就停下来,如果链条末端也没有(即 null
),就返回 undefined
。
构造函数、prototype 和实例对象的关系
1 | function Animal() {} |
它们之间的关系可以总结为:
dog.__proto__ === Animal.prototype
Animal.prototype.constructor === Animal
这意味着构造函数通过 .prototype
定义了实例对象共享的属性或方法,实例对象通过 __proto__
访问到这些内容。
总结一下
- 每个对象都有
__proto__
,指向它的原型对象; - 每个函数都有
prototype
,创建出来的对象的__proto__
就是这个prototype
; - 对象的属性查找是沿着原型链逐级查找的;
- 原型链的尽头是
null
。