摘要:是對象的一個實例,并且的??梢宰约憾x它的屬性,可寫可配可枚舉,均可自己定義,實現(xiàn)一條龍自助服務。這種方式比較適合父類為同級別,子類只要擁有相同的屬性和方法即可的情況。如有異議處,歡迎大家指出來,一起探討。
同事前幾天去面試,回來同步了一下面試題庫,其中一道題就是”new和Object.create的區(qū)別”。聽到這個題目,我的第一個反映是 , what?( ???°_°??? ), Object.create這個東東我沒有用過,怎么回答。為了避免無法給出response的尷尬,老夫抓緊一切時間開始在console里演示著。
-> demo <-
function Person(name, sex) { this.name = name; this.sex = sex; } Person.prototype.getInfo = function() { console.log("getInfo: [name:" + this.name + ", sex:" + this.sex + "]"); } var a = new Person("jojo", "femal"); var b = Object.create(Person.prototype);
-> 分析 <-
赤裸裸的結(jié)果,a就是對象Person的實例,a.__proto__ === Person.prototype。what about b ? b是對象F的一個實例,并且b.__proto__ === Person.prototype的。
這個F到底是個啥呢? 好了,又到了copy-paste時間了,參考了https://developer.mozilla.org... 其實現(xiàn)的polyfill方法:
if (typeof Object.create !== "function") { //此方法未考慮create的第二個參數(shù)的實現(xiàn) Object.create = function (proto, propertiesObject) { if (typeof proto !== "object" && typeof proto !== "function") { throw new TypeError("Object prototype may only be an Object: " + proto); } else if (proto === null) { throw new Error("This browser"s implementation of Object.create is a shim and doesn"t support "null" as the first argument."); } if (typeof propertiesObject != "undefined") throw new Error("This browser"s implementation of Object.create is a shim and doesn"t support a second argument."); //實現(xiàn)一個隱藏函數(shù) function F() {} //函數(shù)的原型設置為參數(shù)傳進來的原型 F.prototype = proto; // 返回一個F函數(shù)的實例,即此實例的__proto__指向為參數(shù)proto return new F(); }; }
好吧,既然都看了polyfill了,就知道Object.create到底是干啥的了,它就是生成了一個實例,這個實例的原型由我來指定,但是它的構(gòu)造函數(shù)F被隱藏了。那下面我們來驗證一下是不是這個邏輯。
通過Object.create()生成的實例怎么才能有自己的屬性呢,別怕,我們看一下它完成的面目是怎樣的,撒花,揭幕~~Object.create(proto, [propertiesObject]), 人家是有第二個參數(shù)滴。可以自己定義它的屬性,可寫、可配、可枚舉,均可自己定義,實現(xiàn)一條龍自助服務。
var b = Object.create(Person.prototype, { name: { value: "coco", writable: true, configurable: true, enumerable: true, }, sex: { enumerable: true, get: function(){ return "hello sex"}, set: function(val){console.log("set value:" + val)} } })
-> 更進一步 <-
說了這么多,那Object.create的應用價值到底是什么呢? 看一下本文標題就知道了,當然說的是繼承了,操刀試一下。
function Student(name, sex, age) { Person.call(this, name, sex); this.age = age; } //原型鏈拼接 Student.prototype = Object.create(Person.prototype); //構(gòu)造函數(shù)彎了,糾正 Student.prototype.constructor = Student; Student.prototype.getInfo = function() { console.log("getInfo: [name:" + this.name + ", sex:" + this.sex + ", age:" +this.age + "]."); } var s = new Student("coco", "femal", 25);
s是Student的實例,Person.prototype在s的原型鏈上,并且這個F實例的constructor又指回了Student。
既然說到了這里,那如果想要一個對象繼承多個類怎么辦呢?在上面的代碼基礎上使用mixin加工下就可啦。
//再創(chuàng)建一個基類 function Animal(age) { this.age = age; } Animal.prototype.say = function(language) { console.log("you say " + language); } function Student(name, sex, age) { Person.call(this, name, sex); Animal.call(this, age); } //原型鏈拼接 Student.prototype = Object.create(Person.prototype); Object.assign(Student.prototype, Animal.prototype); Student.prototype.constructor = Student; Student.prototype.getInfo = function() { console.log("getInfo: [name:" + this.name + ", sex:" + this.sex + ", age:" +this.age + "]."); }; var s = new Student("coco", "femal", 25);
s的原型仍是一個F實例,其原型指向了Person,但是這個F實例上mixin了Animal的方法。但是原型鏈上并沒有Animal什么事,通過instanceof可以驗證這一點。這種方式比較適合父類為同級別,子類只要擁有相同的屬性和方法即可的情況。
如有異議處,歡迎大家指出來,一起探討。學習費腦掉了好多頭皮屑,不過今天又可以碎個覺了。
∧__∧
( ●ω●)
|つ/(___
/└-(____/bug>>>bug>>bug>bug
 ̄ ̄ ̄ ̄ ̄ ̄
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/94589.html
摘要:通過新增方法規(guī)范了原型式繼承。適用場景在沒有必要興師動眾地創(chuàng)建構(gòu)造函數(shù),而只想讓一個對象與另外一個對象保持類似的情況下,原型式繼承是完全可以勝任的。在主要考慮對象而不是自定義類型和構(gòu)造函數(shù)的情況下,寄生式繼承也是一種有用的模式。 --前言:最近在細讀Javascript高級程序設計,對于我而言,中文版,書中很多地方翻譯的差強人意,所以用自己所理解的,嘗試解讀下。如有紕漏或錯誤,會非常感...
摘要:原型鏈與繼承當談到繼承時,只有一種結(jié)構(gòu)對象。如果對該圖不怎么理解,不要著急,繼續(xù)往下看基于原型鏈的繼承對象是動態(tài)的屬性包指其自己的屬性。當使用操作符來作用這個函數(shù)時,它就可以被稱為構(gòu)造方法構(gòu)造函數(shù)。 原型鏈與繼承 當談到繼承時,JavaScript 只有一種結(jié)構(gòu):對象。每個實例對象(object )都有一個私有屬性(稱之為proto)指向它的原型對象(prototype)。該原型對象也...
摘要:并且用驗證了中一系列的實質(zhì)就是魔法糖的本質(zhì)。抽絲剝繭我們首先看的編譯結(jié)果這是一個自執(zhí)行函數(shù),它接受一個參數(shù)就是他要繼承的父類,返回一個構(gòu)造函數(shù)。 如果你已經(jīng)看過第一篇揭秘babel的魔法之class魔法處理,這篇將會是一個延伸;如果你還沒看過,并且也不想現(xiàn)在就去讀一下,單獨看這篇也沒有關系,并不存在理解上的障礙。 上一篇針對Babel對ES6里面基礎class的編譯進行了分析。這一篇將...
摘要:通常有這兩種繼承方式接口繼承和實現(xiàn)繼承。理解繼承的工作是通過調(diào)用函數(shù)實現(xiàn)的,所以是寄生,將繼承工作寄托給別人做,自己只是做增強工作。適用基于某個對象或某些信息來創(chuàng)建對象,而不考慮自定義類型和構(gòu)造函數(shù)。 一、繼承的概念 繼承,是面向?qū)ο笳Z言的一個重要概念。通常有這兩種繼承方式:接口繼承和實現(xiàn)繼承。接口繼承只繼承方法簽名,而實現(xiàn)繼承則繼承實際的方法。 《JS高程》里提到:由于函數(shù)沒有簽名,...
閱讀 2602·2021-10-11 10:59
閱讀 2741·2021-09-22 15:49
閱讀 2675·2021-08-13 13:25
閱讀 1312·2019-08-30 13:14
閱讀 2420·2019-08-29 18:45
閱讀 3030·2019-08-29 18:36
閱讀 1515·2019-08-29 13:21
閱讀 1185·2019-08-26 11:44