首先看一个构造函数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| function Cat(name, age, sex) { this.name = name this.age = age this.sex = sex this.eat = catEat }
function catEat () { console.log(this.name + '吃吃吃') }
let c1 = new Cat('小花', 3, '母') let c2 = new Cat('小绿', 1, '公')
console.log(c1.catEat === c2.catEat)
|
每一个构造函数都有一个属性: 原型,或者说原型对象
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
| function Cat(name, age, sex) { this.name = name this.age = age this.sex = sex } Cat.prototype.catEat = function () { console.log(this.name + '吃吃吃') }
let c1 = new Cat('小花', 3, '母') let c2 = new Cat('小绿', 1, '公')
c1.catEat() c2.catEat()
console.log(c1.catEat === c2.catEat)
console.dir(c1);
|
此时,我们可以得出结论。通过Cat对象创建的实例对象,可以访问到Cat.prototype成员
c1.proto 等于 Cat.prototype 属性
当调用对象的属性或者方法时,先去找对象本身的属性/方法 ,如果对象没有该属性或者方法。此时去调用原型中的属性或者方法。如果对象本身没有该属性或者方法,原型中也没有该属性或者方法,此时会报错
对于 对象,原型,构造函数的关系, 我们可以通过一张图表示出来
思考:
原型的构造函数是什么? 原型的原型是什么?
1 2 3 4
| let o = c1.__proto__ console.log(o.__proto__.constructor) console.log(o.__proto__.__proto__)
|
原型对象的proto 为 一个 object 对象,而object 的 原型对象为null。
思考:
当我们构造方法中设置prototype属性时,一个实例对象修改此属性,会对其他实例对象有影响吗?
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| function Cat(name, age, sex) { this.name = name this.age = age this.sex = sex } Cat.prototype.color = 'white'
let c1 = new Cat('小花', 3, '母') let c2 = new Cat('小绿', 1, '公')
c1.color = 'yellow' console.log(c1.color) console.log(c2.color) console.dir(c1) console.dir(c2)
|
得出结论,只有当获取属性时。受到原型影响,设置属性时,只会为c1创建属性,此时不再访问__proto__属性。
只有获取收到影响。