原型规则总结
1、所有的引用类型(对象、数组、函数),都具有对象特性,既可以自由扩展属性(除了 null 以外)
var obj = {};
obj.a = 100;
var arr = [];
arr.a = 100;
function fn(){}
fn.a = 100;
2、所有的引用类型(对象、数组、函数),都有一个__proto__属性,属性值是一个普通对象。(__proto__称为 隐式原型)(除了 null 以外)
console.log(obj.__proto__);
console.log(arr.__proto__);
console.log(fn.__proto__);
3、所有的函数,都有一个prototype属性,属性值也是一个普通对象。(prototype 称为 显示原型)
console.log(fn.prototype);
4、所有的引用类型(对象、数组、函数),__proto__(隐式原型)属性值指向它的构造函数的 prototype (显示原型)属性值
console.log(obj.__proto__ === Object.prototype);
5、当试图得到一个 引用类型(对象、数组、函数)的某个属性时,如果这个对象本身没有这个属性,那么会去它的 __proto__(即它的构造函数的 prototype )中寻找
(构造函数的 prototype 显示原型和它自身的 __proto__ 隐式原型是一回事)
//构造函数
function Fn (name,age){
this.name = name;
}
//显示原型
Fn.prototype.alertName = function(){
alert(this.name);
}
//创建实力
var f = new Fn('clm');
f.printName = function(){
console.log(this.name);
}
f.printName();// clm
//f 没有 alertName 这时候会去它的 __proto__ 隐式原型中寻找 当前的隐式原型指向它的构造函数 prototype 显示原型中寻找
//this 补充 通过对象属性去执行函数的时候,无论函数是一个自身的属性,还是从它的原型中得到的属性,它这个函数在执行当中这个this永远指向它本身。
//在执行f.alertName()时候,alert(this.name); 这个this就是f
f.alertName();// clm
6、class
每个class都有显示原型prototype
每个实例都有隐式原型__proto__
实例的__proto__指向对应class的prototype
获取属性或执行方法时,先在自身属性和方法寻找,如果找不到则自动去__proto__ (隐式原型) 中查找