要執(zhí)行的代碼
function Dog(name) {
this.name = name;
}
Dog.prototype.bark = function () {
console.log('wangwang');
}
Dog.prototype.sayName = function () {
console.log('my name is ' + this.name);
}
let sanmao = _new(Dog, '三毛');
sanmao.bark(); //=>"wangwang"
sanmao.sayName(); //=>"my name is 三毛"
console.log(sanmao instanceof Dog); //=>true */
第一種new創(chuàng)建的過(guò)程代碼執(zhí)行:
// Ctor -> constructor縮寫(xiě) 構(gòu)造函數(shù)
// params -> 后期給Ctor傳遞的所有的實(shí)參信息
function _new(Ctor, ...params) {
// 1.創(chuàng)建Ctor的一個(gè)實(shí)例對(duì)象
// 實(shí)例.__proto__===Ctor.prototype
let obj = {};
obj.__proto__ = Ctor.prototype;
// 2.把構(gòu)造函數(shù)當(dāng)做普通函數(shù)執(zhí)行「讓方法中的THIS->實(shí)例對(duì)象」
let result = Ctor.call(obj, ...params);
// 3.確認(rèn)方法執(zhí)行的返回值「如果沒(méi)有返回值或者返回的是原始值友存,我們讓其默認(rèn)返回實(shí)例對(duì)象即可...」
if (result !== null && /^(object|function)$/.test(typeof result)) return result;
return obj;
}
優(yōu)化版本:
function _new(Ctor, ...params) {
let obj,
result,
proto = Ctor.prototype,
ct = typeof Ctor;
// 校驗(yàn)規(guī)則
if (Ctor === Symbol || Ctor === BigInt || ct !== 'function' || !proto) throw new TypeError(`${Ctor} is not a constuctor!`);
obj = Object.create(Ctor.prototype);
result = Ctor.call(obj, ...params);
if (result !== null && /^(object|function)$/.test(typeof result)) return result;
return obj;
}
Object.create([obj])解釋:
Object.create([obj]):創(chuàng)建一個(gè)空對(duì)象祷膳,并且讓空對(duì)象.proto指向[obj] “把[obj]作為新實(shí)例對(duì)象的原型”
- [obj]可以是一個(gè)對(duì)象或者是null屡立,但是不能是其他的值
- Object.create(null) 創(chuàng)建一個(gè)不具備proto屬性的對(duì)象「不是任何類的實(shí)例」
面試題:
// 面試題:重寫(xiě)Object.create()
Object.create = function create(prototype) {
if (prototype !== null && typeof prototype !== "object") throw new TypeError('Object prototype may only be an Object or null');
var Proxy = function Proxy() {}
Proxy.prototype = prototype;
return new Proxy;
};