prototype原型对象模式的概念,在JavaScript中是很重要的,尤其在VUE原型链的学习理解中极其重要,理解如下:
1、prototype
属性(显式原型)
我们在js中创建函数,都有一个prototype
属性,可称为显式原型,这个属性是一个指针,指向一个对象(原型对象),这个对象包含了通过调用该构造函数所创建的对象共享的属性和方法。
prototype
是构造函数的属性,指向原型对象
// 构造函数
function Person(name,age){
this.name=name
this.age=age
}
- 我们创建了一个函数,此时,系统自动帮我们创建了一个和这个函数对应的原型对象
- 我们创建的函数,有了一个属性
prototype
,指向了原型对象 - 所有的对象实例,都可以共享原型对象包含的属性和方法。
我们来证明一下:
function Person(name,age){
this.name=name
this.age=age
}
// 给原型对象添加一个方法 say
Person.prototype.say=function(){
console.log("hello world")
}
var p1= new Person("张三",18)
p1.say()
var p2= new Person("李四",21)
p2.say()
2、__proto__
属性(隐式原型)
对象具有属性__proto__
,可称为隐式原型,一个对象的隐式原型指向构造该对象的构造函数的原型对象,这也保证了实例能够访问在构造函数原型中定义的属性和方法。
我们打印刚刚实例化的对象:p1 和 p2
在这里,并没有发现刚刚调用的方法say()
我们展开[[protype]]
发现了刚刚调用的方法say()
,而这里的[[protype]]
就是__proto__
该属性不是web标准,即将被抛弃,只能在学习研究方便理解时候用,在实际开发的时候,不建议使用
所以,得到结论:
证明:
console.log("原型对象类型",typeof Person.prototype)
console.log("构造函数类型",typeof Person)
console.log("构造函数与原型对象一致吗?",Person.prototype===Person)
console.log("prototype与__proto__指向一致吗?",Person.prototype===p1.__proto__)
console.log("prototype与__proto__指向一致吗?",Person.prototype===p2.__proto__)
3、原型链理论
JavaScript 对象有一个指向一个原型对象的链。
当试图访问一个对象的属性时,它不仅仅在该对象上搜寻,还会搜寻该对象的原型,以及该对象的原型的原型,依次层层向上搜索,直到找到一个名字匹配的属性或到达原型链的末尾。
所以,刚刚我们实例化的对象:p1 和 p2,我们调用他们身上的say()方法时,自身没有,就搜寻原型,在原型中找到,即开始执行。