关于原型链的解释(三)

七. 函数对象
所有的构造器都来自于 Function.prototype,甚至包括根构造器Object及Function自身。所有构造器都继承了·Function.prototype·的属性及方法。如length、call、apply、bind。

所有构造器(含内置及自定义)的__proto__都是Function.prototype,那Function.prototype的__proto__是谁呢?如下console.log(Function.prototype.proto === Object.prototype) // true这说明所有的构造器也都是一个普通 JS 对象,可以给构造器添加/删除属性等。同时它也继承了Object.prototype上的所有方法:toString、valueOf、hasOwnProperty等。
最后Object.prototype的proto是谁?Object.prototype.proto === null // true已经到顶了,为null

八. Prototype
toString()和 valuseOf() 等方法实际上都保存在 prototype 名下
var Person = new Object()Person 是 Object 的实例,所以 Person 继承了Object 的原型对象Object.prototype上所有的方法:

Object.getOwnPropertyNames获取所有(包括不可枚举的属性)的属性名不包括 prototy 中的属性,返回一个数组:

var arrayAllKeys = Array.prototype; // [] 空数组
// 只得到 arrayAllKeys 这个对象里所有的属性名(不会去找 arrayAllKeys.prototype 中的属性)
console.log(Object.getOwnPropertyNames(arrayAllKeys)); 
/* 输出:
["length", "constructor", "toString", "toLocaleString", "join", "pop", "push", 
"concat", "reverse", "shift", "unshift", "slice", "splice", "sort", "filter", "forEach", 
"some", "every", "map", "indexOf", "lastIndexOf", "reduce", "reduceRight", 
"entries", "keys", "copyWithin", "find", "findIndex", "fill"]
*/
var num = [1];
console.log(num.hasOwnPrototype()) // false (输出布尔值而不是报错)可以通过这个判断,这个属性是实例的,还是原型的。
 Array.prototype 继承了对象的所有方法,当你用num.hasOwnPrototype()时,JS 会先查一下它的构造函数 (Array) 的原型对象 Array.prototype 有没有有hasOwnPrototype()方法,没查到的话继续查一下 Array.prototype 的原型对象 Array.prototype.__proto__有没有这个方法。
所有函数对象****proto都指向 Function.prototype,它是一个空函数(Empty function
所有对象的 __proto__ 都指向其构造器的 prototype
 JS 内置构造器:
var obj = {name: 'jack'}
var arr = [1,2,3]
var reg = /hello/g
var date = new Date
var err = new Error('exception')
 
console.log(obj.__proto__ === Object.prototype) // true
console.log(arr.__proto__ === Array.prototype)  // true
console.log(reg.__proto__ === RegExp.prototype) // true
console.log(date.__proto__ === Date.prototype)  // true
console.log(err.__proto__ === Error.prototype)

九. 原型链

function Person(){}
var person1 = new Person();
console.log(person1.__proto__ === Person.prototype); // true
console.log(Person.prototype.__proto__ === Object.prototype) //true
console.log(Object.prototype.__proto__) //null

Person.__proto__ == Function.prototype; //true
console.log(Function.prototype)// function(){} (空函数)

var num = new Array()
console.log(num.__proto__ == Array.prototype) // true
console.log( Array.prototype.__proto__ == Object.prototype) // true
console.log(Array.prototype) // [] (空数组)
console.log(Object.prototype.__proto__) //null

console.log(Array.__proto__ == Function.prototype)// true

Object.proto === Function.prototype // trueObject 是函数对象,是通过new Function()创建的,所以Object.__proto__指向Function.prototype。(参照第八小节:「所有函数对象的__proto__都指向Function.prototype」)

Function.proto === Function.prototype // trueFunction 也是对象函数,也是通过new Function()创建,所以Function.__proto__指向Function.prototype。

Function.prototype.__proto__ === Object.prototype //true

总结:
原型和原型链是JS实现继承的一种模型。
原型链的形成是真正是靠__proto__ 而非prototype
实例(person1)和 原型对象(Person.prototype)存在一个连接。不过,要明确的真正重要的一点就是,这个连接存在于实例(person1)与构造函数的原型对象(Person.prototype)之间,而不是存在于实例(person1)与构造函数(Person)之间。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值