-
Notifications
You must be signed in to change notification settings - Fork 0
Open
Description
新的一年,新的开始。最近的开发过程越来越感觉基础不够扎实,很多知识的理解都很片面,所以打算以这一个系列开始自己的基础夯实之路,希望自己能坚持下去。
手动实现 new
new 的原理
new 的作用是实例化一个类,所以紧接的必须是一个构造函数(或者 class)。
具体执行过程:
- 创建一个空对象
- 将该对象的
__proto__
属性指向构造函数的prototype
- 构造函数的执行上下文指向该对象,然后执行构造函数
- 如果构造函数的返回结果是对象,则直接返回这个对象;否则隐式返回最开始创建的那个对象。
具体代码实现如下:
/**
* 手动实现 new 操作符
* @param {*} fn 构造函数,第二个及后面的参数传递给构造函数
*/
function New(fn) {
const instance = {}
instance.__proto__ = fn.prototype
const args = Array.prototype.slice.call(arguments, 1)
const res = fn.apply(instance, args)
// 如果构造函数有返回值并且为对象时,直接用该返回值,否则返回前面生成的实例
if (res !== null && (typeof res === 'object' || typeof res === 'function')) {
return res
}
return instance
}
// test
function Dog(name) {
this.name = name
}
var dog = New(Dog, 'Tony')
console.log(dog.name) // 'Tony'
console.log(dog instanceof Dog) // true
手动实现 instanceof
instanceof 原理
instanceof 用于判断左侧值是否是右侧值的实例,所以左侧必须是一个对象,而右侧是一个类。
具体原理是 instanceof 会查找原型链,知道 null 之前如果还不是这个对象的实例则会返回 false,否则返回 true
具体实现:
/**
*
* @param {*} instance 实例
* @param {*} clazz 类
*/
function instanceOf(instance, clazz) {
if ( typeof clazz !== 'function') throw new Error('Right-hand error')
if (instance === null || (typeof instance !== 'object' && typeof instance !== 'function')) return false
const proto = clazz.prototype
while (instance.__proto__) {
if (instance.__proto__ === proto) return true
instance = instance.__proto__
}
return false
}
// test
var one = new Number(1)
console.log(
instanceOf(one, Number), // true
instanceOf(one, Object) // true
)