prototype属于构造函数,指向原型对象
__proto__属于实例对象,指向原型对象
打印实例对象的时候,可以看到,这个[[prototype]],并不是真正的原型对象,它的名字其实是__proto__
,被隐藏了。真正的原型对象,是在控制台中console.dir(构造函数)
,打印出来的,是没有两侧的中括号的
在最新版的谷歌浏览器中,打印实例对象的时候,p1.prototype
,是undefined,谷歌浏览器把这个属性屏蔽了。只能通过p1.__proto__
查看。
实例对象访问其中的原型对象方法,实际是通过p1.__proto__.eat()
访问的。但已经不推荐使用了,具体见mdn。该属性不是web标准属性,在浏览器中看不见,但是代码可以用,实际开发中不要使用
作用是让实例对象访问原型对象的成员。
属于函数的属性,就叫静态成员。属性+方法统称为成员变量
实例成员就是属于实例对象的成员
函数也可以像对象一样添加成员
function Person(name, age) {
this.name = name
this.age = age
}
//静态成员
console.log(Person.prototype)
Person.aaa = '111'
console.dir(Person)
上面的aaa就是静态成员
函数是一种特殊的类型,通过console.log只能看到其中的代码,不能看到内存数据。还有个特殊的就是new data()
,只能看到字符串,不能看到内存。想看内存,可以通过console.dir
constructor属于原型对象,指向构造函数
打印构造函数.prototype
,可以看到其中的原型对象方法和constructor,作用是可以让实例对象知道自己是被谁创建的console.log(p1.constructor)
,它虽然属于原型,但实例可以无条件的用原型中的方法。完整的写法可以是p1.__proto__.constructor
constructor的作用主要是给构造函数添加新的方法:
通过实例对象a给a的构造函数(a的爹)添加方法,则同样继承的实例对象b,就可以b.log2();
a.constructor.prototype.log2 = function () {
console.log(this.b)
}
理解
怎么理解其中的属性呢。两者结婚后,双方的持证人,和配偶是不同的
prototype相当于老婆,constructor相当于叫老公,__proto__相当于叫妈。孩子想知道自己的亲生父亲是谁,只能用妈妈的constructor去找。
console.log(p1._proto_.constructor ===Person ) //true 证明是亲爹
console.log(p1._proto_===Person.prototype) //true 证明是亲妈