成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

JavaScript面向?qū)ο驩OM 2(JavaScript 創(chuàng)建對象的工廠模式和構(gòu)造函數(shù)模式)

you_De / 2396人閱讀

摘要:都是構(gòu)造函數(shù)模式創(chuàng)建的原生構(gòu)造函數(shù)。使用構(gòu)造函數(shù)創(chuàng)建對象經(jīng)歷了以下四個過程創(chuàng)建一個新對象構(gòu)造函數(shù)的作用域交給新對象。

??在創(chuàng)建對象的時候,使用對象字面量和 new Object() 構(gòu)造函數(shù)的方式創(chuàng)建一個對象是最簡單最方便的方式。但是凡是處于初級階段的事物都會不可避免的存在一個問題,沒有普適性,意思就是說我要為世界上(程序中)的所有使用到的對象都使用一遍 var xxx = {} ,對于"懶惰"的程序員來講是不可以接受的。即便你能接受這種創(chuàng)建的方式,也無法保證將所有對象歸類這一哲學(xué)問題。

??由此,優(yōu)秀的程序員們利用現(xiàn)有的規(guī)則,創(chuàng)造出了一種種優(yōu)秀的解決方案 -- 這些優(yōu)秀的解決方案統(tǒng)稱為設(shè)計模式。

??在 JavaScript 中,設(shè)計模式由初級到高級的區(qū)別是他們的副作用的大小。依次可以分為:

工廠模式

構(gòu)造函數(shù)模式

原型模式

others

??同時,使用設(shè)計模式也可以優(yōu)雅的解決 JavaScript 在 ES6之前都是沒有類的尷尬問題。

工廠模式

??工廠模式,顧名思義就是創(chuàng)建對象的一個工廠,工廠可以創(chuàng)造一類具有相似結(jié)構(gòu)和功能的對象。這個模式的誕生也基本解決了:

創(chuàng)建多個對象的時候,需要大量重復(fù)代碼

先看下在這種設(shè)計模式下,應(yīng)該如何組織我們的代碼:

function createPerson(name, age) {
    var obj = new Object();
    
    obj.name = name ;
    obj.age  = age;
    obj.say  = function() { console.log(this.name)}
    
    return obj;
}

var p1 = createPerson("ZhangSan", 12);
p1.say()  //ZhangSan

這種叫工廠模式的設(shè)計模式:是指使用統(tǒng)一的方法(函數(shù),因為 Js 沒有類)來描述對象創(chuàng)建的細節(jié)

把這個對象封裝起來,每次使用類似的對象都使用這個工廠函數(shù)來創(chuàng)建。

它抽象了創(chuàng)建一個對象的過程。

當然,處于初級階段的 工廠模式, 一定有它處于初級階段的道理:

優(yōu)勢:

工廠函數(shù)可以解決創(chuàng)建多個類似功能對象的問題。

缺點:

工廠模式無法解決對象的識別問題: 不知道對象是什么類型的。

使用工廠函數(shù)創(chuàng)建的對象,只有開發(fā)者是知道它的類型的(通過工廠函數(shù)變量名),但是程序仍然認為它是一個普通的對象。

每個對象都是通過工廠造就的全新的對象。

構(gòu)造函數(shù)模式

??在 JavaScript 的開發(fā)中,經(jīng)常會聽說和使用的一個詞語叫做構(gòu)造函數(shù),這里的構(gòu)造函數(shù)就是出自構(gòu)造函數(shù)模式這一種設(shè)計模式。在長時間的傳承中,文化或者其他的名詞都會變成一種泛稱,所以人們常說的構(gòu)造函數(shù),有的時候指的是構(gòu)造函數(shù)模式,有的時候指的是構(gòu)造函數(shù)模式創(chuàng)造的對象中的構(gòu)造函數(shù)方法(實例的 constructor )。

??構(gòu)造函數(shù)是用來創(chuàng)建特定的類型的對象的。比如Js原生提供的ObjectArray。都是構(gòu)造函數(shù)模式創(chuàng)建的原生構(gòu)造函數(shù)。

慣例,看下在這種設(shè)計模式下,該如何組織代碼:

function Person (name, age) {

    this.name = name;
    this.age = age;
    this.say = function() {
        console.log(this.age);
    }
    
}

var p1 = new Person("ZhangSan", 12);
var p2 = new Person("LiSi", 22);
p1.say() // 12
p2.say() // 22

使用構(gòu)建函數(shù)模式和工廠模式創(chuàng)建對象的區(qū)別:

沒有明顯的創(chuàng)建對象的過程: (new Object()的過程)

直接將參數(shù)賦值給了 this。(因為 沒有創(chuàng)建明顯的對象,就需要用 this 進行賦值)

沒有 return 。

構(gòu)造函數(shù)的首字母大寫,這是代碼風(fēng)格上的變化(為了和其他的 OOM 語言的代碼風(fēng)格保持一致)

創(chuàng)建一個由構(gòu)造函數(shù)創(chuàng)建的對象,需要使用 new Person() 進行創(chuàng)建。

使用構(gòu)造函數(shù)創(chuàng)建對象經(jīng)歷了以下四個過程:

創(chuàng)建一個新對象

構(gòu)造函數(shù)的作用域交給新對象。this指向新對象

執(zhí)行內(nèi)部代碼,給新對象增加屬性和方法

返回新對象

由構(gòu)造函數(shù)創(chuàng)建的對象稱為這個構(gòu)造函數(shù)的實例,在實例中會存在一個 constructor 屬性,這個屬性指向創(chuàng)造它的構(gòu)造函數(shù)。(證明自己從哪里來)

p1.constructor == Person;  // true
p2.constructor == Person;  // true

每一個實例都是可以被檢測出來的,檢測對象是否屬于某一個類型,可以使用 instanceof XX。

    p1 instanceof Person // true
    p1 instanceof Object // true

知道了構(gòu)造函數(shù)模式創(chuàng)建實例的過程和方法,下面介紹一些使用構(gòu)造函數(shù)方法中,一些不為人知的秘密(高級知識點):

使用構(gòu)造函數(shù)的時候常規(guī)操作是:使用操作符new。但是也可以直接當做一個普通的函數(shù)使用。

// Person 在上個 Demo
    
var p3 = Person("Person3", 33);
p3; // undefined;
p3.say(); // undefined;
    
Person("Person4", 44);
window.say(); // 44;
    

如果把構(gòu)造函數(shù)當做普通函數(shù)使用了,就不能構(gòu)造實例了,即使構(gòu)造了實例,也都是 undefined。

直接使用 構(gòu)造函數(shù)當做普通函數(shù)使用, 屬性和方法會被添加到全局中(window/global)。

當然也可以使用 call把 this 指向其他對象。(不了解 call,可以先忽略。call 是改變 this 指針的方式之一)。

??了解了高級用法之后,細心的孩子已經(jīng)發(fā)現(xiàn)了構(gòu)造函數(shù)方法作為 Level 2的設(shè)計模式,一定有哪里不對。其實很簡單,在構(gòu)造函數(shù)創(chuàng)建的過程中,很好的解決了工廠模式創(chuàng)建對象不知道類型的問題(不知道自己從哪里來)。在構(gòu)想上,實例的屬性和方法應(yīng)該都是唯一指向的,理想情況是都指向構(gòu)造函數(shù)。但是差強人意的地方出現(xiàn)了:

屬性都很好的指向了 構(gòu)造函數(shù)。 this.name = name

方法又自己偷摸的創(chuàng)建了新的對象(函數(shù)也是對象)。這就不符合理想的情況了,因為這個時候:

p1.say === p2.say   // false

原理也很清楚啊:this.say = function() {} 就是 this.say = new Function() 啊。

這個時候,一個構(gòu)造函數(shù)的補救措施出現(xiàn)了:

var Person = function(name, age) {
    this.name = name;
    this.age = age;
    this.say = sayFunc;
}

var sayFunc = function() {
    console.log(this.age)
}

使用額外的函數(shù),將構(gòu)造函數(shù)內(nèi)的方法指向外部,這樣就保證了實例方式的相同。

俗話說的好,補救措施終究是補救措施

在構(gòu)造函數(shù)存在大量的方法的時候,外部會存在數(shù)量巨多的補救方法。

補救方法在構(gòu)造函數(shù)的外部,毫無封裝性可言。

外部方法也是一個普通的函數(shù),也可以被其他方法或構(gòu)造函數(shù)執(zhí)行。

外部方法被添加到 全局(window/global)上,性能浪費。如果在 window 上調(diào)用,this 就指向了 window。造成 this 指向混亂(誰調(diào)用,this 指向誰)

所以,構(gòu)造函數(shù)的方法仍然是一個不完美的方法。但是在開發(fā)速度上,構(gòu)造函數(shù)的設(shè)計模式還是有很大優(yōu)勢的。

而且當你需要你的方法在全局被使用的時候,構(gòu)造函數(shù)模式是最適合的,這也是 Object, Array原生構(gòu)造函數(shù)出現(xiàn)的原因。

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/53217.html

相關(guān)文章

  • JavaScript面向對象OOM 2JavaScript 創(chuàng)建對象工廠模式構(gòu)造函數(shù)模式

    摘要:都是構(gòu)造函數(shù)模式創(chuàng)建的原生構(gòu)造函數(shù)。使用構(gòu)造函數(shù)創(chuàng)建對象經(jīng)歷了以下四個過程創(chuàng)建一個新對象構(gòu)造函數(shù)的作用域交給新對象。 ??在創(chuàng)建對象的時候,使用對象字面量和 new Object() 構(gòu)造函數(shù)的方式創(chuàng)建一個對象是最簡單最方便的方式。但是凡是處于初級階段的事物都會不可避免的存在一個問題,沒有普適性,意思就是說我要為世界上(程序中)的所有使用到的對象都使用一遍 var xxx = {} ,...

    liuchengxu 評論0 收藏0
  • JavaScript面向對象程序設(shè)計

    摘要:目錄導(dǎo)語理解對象和面向?qū)ο蟮某绦蛟O(shè)計創(chuàng)建對象的方式的繼承機制原型對象原型鏈與原型對象相關(guān)的方法小結(jié)導(dǎo)語前面的系列文章,基本把的核心知識點的基本語法標準庫等章節(jié)講解完本章開始進入核心知識點的高級部分面向?qū)ο蟮某绦蛟O(shè)計,這一部分的內(nèi)容將會對對象 目錄 導(dǎo)語 1.理解對象和面向?qū)ο蟮某绦蛟O(shè)計 2.創(chuàng)建對象的方式 3.JavaScript的繼承機制 3.1 原型對象 3.2 原型鏈 3.3 與...

    gitmilk 評論0 收藏0
  • 我來重新學(xué)習(xí) javascript 面向對象(part 1)

    摘要:其實在之前的工廠模式里面,也存在這個問題,不過工廠模式更徹底,直接完全創(chuàng)建一個新對象,而構(gòu)造函數(shù)模式的話只是方法會被重新創(chuàng)建。 我來重新學(xué)習(xí) javascript 的面向?qū)ο螅╬art 1) 很多job 的描述都說要求精通 javascript 面向?qū)ο缶幊?,但是根?jù)一般的套路,寫精通其實就是熟練,寫熟練其實就是一般,寫一般其實就是懵逼! showImg(https://segment...

    myshell 評論0 收藏0
  • 【9】JavaScript 面向對象高級——對象創(chuàng)建模式

    摘要:解決了構(gòu)造函數(shù)模式不能共享方法的問題。六寄生構(gòu)造模式流程創(chuàng)建一個構(gòu)造函數(shù),在這個函數(shù)內(nèi)部創(chuàng)建一個對象,用返回對象。除了使用操作符并把使用的包裝函數(shù)叫做構(gòu)造函數(shù)以外,這個模式與工程模式其實是一模一樣的。 JavaScript面向?qū)ο蟾呒墶獙ο髣?chuàng)建模式 一、工廠模式 流程: 定義一個函數(shù),函數(shù)返回對象。 適用場景: 需要創(chuàng)建多個對象,都是Object類型。 優(yōu)點:完成了返回一個對象的...

    linkin 評論0 收藏0
  • JavaScript面向對象 - 創(chuàng)建對象(上)

    摘要:對象字面量創(chuàng)建對象張三學(xué)生這種方式的好處顯而易見,就是解決了之前的缺點。構(gòu)造函數(shù)模式張三學(xué)生李四學(xué)生與之前工廠模式的方法對比變量名首字母大寫了在函數(shù)內(nèi)沒有顯式的創(chuàng)建及返回對象而使用了創(chuàng)建時使用了關(guān)鍵字。 面向?qū)ο笫荍S的重點與難點,但也是走向掌握JS的必經(jīng)之路,有很多的文章或書籍中都對其進行了詳細的描述,本沒有必要再寫這些,但是對于學(xué)習(xí)來說,講給別人聽對自己來說是一種更好的受益方式。我...

    sourcenode 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<