彻底搞懂JS 原型链
// JS 道德经 混沌是什么? 混沌是null, 混沌中产生道。
// 道是什么? 道是Object.prototype 。它是最原始的对象。
console.log('Object.prototype.__proto__ is:', Object.prototype.__proto__) // null
// 先有Object.prototype ,它只包含最原始的对象的基本方法。// {constructor: ƒ, __defineGetter__: ƒ, __defineSetter__: ƒ, hasOwnProperty: ƒ, __lookupGetter__: ƒ, …}
// 不同浏览器可能不一样,有些浏览器返回为{}
console.log('Object.prototype is:', Object.prototype)
// 道生一,一是什么?一是 Function.prototype。原型就一对象、而且有个属性__proto__,指向Object.prototype。
console.log(Function.prototype.__proto__ === Object.prototype) // true
// 一生二,二是什么?二是:Function.和Object,它是两套机制。本质上Object为Function定义的用来定义对象的构造函数,所以可以看成Object的构造函数为Function。即:
console.log(Object.__proto__ === Function.prototype) // true, Object对象继承于Function,!函数是对象,对象不是函数的源头
Function也是对象,是对象就有__proto__属性,指向构造它的prototype,
console.log(Function.__proto__ === Function.prototype) // true, 这是最奇怪的地方,Function构造自己。
// 二生万物,也就是两派,object和function,从本质来说,万物归一,就是Function.prototype,也就是说都可以是函数
Function.constructor ===Function // Function.__proto__.constructor ===Function // Function.prototype.constructor ===Function 这三个都是true。
// 即JS中函数是第一公民
// 函数派
var A = new Function('name', 'return ' + '`Hello ${name}!`')
/**
等价于 function A(name) {return `Hello ${name}!`}
**/
console.log(A.__proto__ === Function.prototype) // true
console.log(A.prototype === Function.prototype) // false A.prototype为A对象(函数)挂的,如果不定义,默认只有一个属性constructor,指向它的构造函数。
var a = new A()
console.log('A.prototype is:', A.prototype) // anonymous {} A继承于 Function 只有个属性constructor。
console.log('A.prototype.constructor is:', A.prototype.constructor) // anonymous {}
console.log(a.__proto__ === A.prototype) // true
// a已经是纯粹的实例对象了,它不能被继承,a.prototype 初始是没有的,可以定义。
console.log('a.prototype is:', a.prototype) //undefined
console.log(a instanceof Function) // false
console.log(a instanceof A) // true
var b = function B() {}
/**
等价于 var b = new Function('', return)
等价于
var b = {}
b.__proto__ = Function.prototype
Function.call(b, '')
**/
console.log('b.prototype is:', b.prototype) // {} 对象的prototype没有赋值,
console.log(b.__proto__ === Function.prototype) // true, Function.prototype === Function.__proto__
console.log(b.__proto__ === Function.__proto__) // true
console.log('b.prototype.constructor is:', b.prototype.constructor) // function B{}
// 对象派 Object.create() 和 new Object(), {}
var options = {
'a':'A'
}
// options等价于 options = new Object(),options.a = 'A'
var obj = Object.create(options) // obj.prototype = options这个是create的语法,需要牢记。
obj.b = 'B'
console.log(obj.__proto__) // { a: 'A' } // 父类
// 和Function实例一致,属性Object的实例。初始是没有prototype,
console.log(obj.prototype) // undefined 没有定义
console.log(options.__proto__) // {} 回到了道 Object.prototype
var obj = new Object()
obj.b = 'B'
console.log(obj.__proto__); // {}
console.log(obj.prototype) // undefined,
console.log({}.prototype) // undefined 等价, 这里与function不同
// 难点: Function.prototype 生 Object 和 Function的过程
附图:


浙公网安备 33010602011771号