记得有一次面试, 就考到了原型链. 面试官在批改个人笔试题时, 他忽然说你这题是作对了, 那你把它完整的原型链画出来吧! 难受😣, 当时我也是只知其一;不知其二的作对了, 我只能瞎操做一顿了.javascript
今天就好好整理下关于原型链
的知识vue
要理解原型链是什么, 就要知道什么是__proto__、什么是prototype、还有constrtctor, 以及他们之间的关系java
一、__proto__
js的Function其实就是一个对象, 那js中的对象有个一特殊[[prototype]]
内置属性, 几乎搜索对象在建立时候 [[prototype]]
都会赋予一个非空的值. 注: [[prototype]]
也就是 __proto__
, 一些书籍上就标记为[[prototype]], 浏览器中为__proto__
. 常说的原型链条就是 [[prototype]]链
或者 __proto__链
.面试
二、prototype浏览器
每一个Function
都会有一个prototype属性, 叫作原型.函数
三、constructorpost
构造函数的prototype
属性的constructor
属性指向其自己(如构造函数Foo, 它的原型上的construstor
(即Foo.prototype.construstor === Foo
)指向它自己; 实例的constructor
指向构造函数自己(即foo.constructor === Foo
)ui
先来一个图热身spa
是否是常常在网上看到一个相似这样的关系图, 各类箭头指来指去的, 感受好难.prototype
其实, 还有更难的
上图你能够先忽略其余的, 先看原型链部分
你能够将箭头理解为一个指向或者理解为它是一个等号, 那就很容易总结出一个规律了. 写了一个构造函数Foo
, 实例化出来一个foo
, foo
上就会有一个__proto__
属性, 指向它的构造函数爸爸
的原型Foo.prototype
, Foo.prototype
上又有一个__proto__
, 指向Foo的爸爸
Object的原型上Object.prototype
, 可怜的是Object已经没有爸爸
了, 最终Object.prototype.__proto__
指向null
, 原型链寻找属性的过程到了null就结束了
简单一点总结就是: 儿子(foo)
的__proto__
指向 爸爸(Foo)
的prototype
, 爸爸的prototype.__proto__
指向爷爷(Object)
的 prototype
, ... 最终指向到null结束
最终出现只样的调用链
foo.__proto__ === Foo.prototype // true
Foo.prototype.__proto__ === Object.prototype // true
Object.prototype.__proto__ === null // true
// 根据上面的关系, 可以得出如下链式
foo.__proto__.__proto__.__proto__ === null // true
复制代码
当咱们去调用一个foo
没有的属性时候, 它会沿着这条链往上去寻找, 找到为止或者找到null
才中止
// 构造函数
function Foo () {
console.log('Foo构造函数')
}
// foo实例
const foo = new Foo()
console.log('一、',foo.__proto__ === Foo.prototype) // true
console.log('二、', Foo.prototype.constructor === Foo) // true
console.log('三、', Foo.prototype.__proto__ === Object.prototype) // true
console.log('四、', Object.prototype.__proto__ === null) // true
console.log('五、', foo.__proto__.__proto__.__proto__ === null) // true
console.log('六、', foo.constructor === Foo.prototype.constructor) // true
console.log('七、', foo.constructor === foo.__proto__.constructor) // true
console.log('八、', foo.constructor === Foo) // true
console.log('九、', Foo.constructor === Object.constructor) // true
console.log('十、', Foo.__proto__ === Function.prototype) // true
console.log('十一、', Function.prototype.__proto__ === Object.prototype) // true
console.log('十二、', Function.__proto__ === Function.prototype) // true
console.log('1三、', Function.constructor === Function) // true
console.log('1四、', Object.constructor === Function) // true
console.log('1五、', Foo.constructor === Function) // true
console.log('1六、', Object.__proto__ === Function.prototype) // true
复制代码
其余文章: