溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

Composite組合模式怎么實(shí)現(xiàn)

發(fā)布時(shí)間:2022-03-25 10:48:42 來源:億速云 閱讀:142 作者:iii 欄目:web開發(fā)

本文小編為大家詳細(xì)介紹“Composite組合模式怎么實(shí)現(xiàn)”,內(nèi)容詳細(xì),步驟清晰,細(xì)節(jié)處理妥當(dāng),希望這篇“Composite組合模式怎么實(shí)現(xiàn)”文章能幫助大家解決疑惑,下面跟著小編的思路慢慢深入,一起來學(xué)習(xí)新知識(shí)吧。

Composite(組合模式)

Composite(組合模式)屬于結(jié)構(gòu)型模式,是一種統(tǒng)一管理樹形結(jié)構(gòu)的抽象方式。

意圖:將對(duì)象組合成樹形結(jié)構(gòu)以表示 “部分 - 整體” 的層次結(jié)構(gòu)。Composite 使得用戶對(duì)單個(gè)對(duì)象和組合對(duì)象的使用具有一致性。

舉例子

如果看不懂上面的意圖介紹,沒有關(guān)系,設(shè)計(jì)模式需要在日常工作里用起來,結(jié)合例子可以加深你的理解,下面我準(zhǔn)備了三個(gè)例子,讓你體會(huì)什么場(chǎng)景下會(huì)用到這種設(shè)計(jì)模式。

公司組織關(guān)系樹

公司組織關(guān)系可能分為部門與人,其中人屬于部門,有的人有下屬,有的人沒有下屬。如果我們統(tǒng)一將部門、人抽象為組織節(jié)點(diǎn),就可以方便的統(tǒng)計(jì)某個(gè)部門下有多少人、財(cái)務(wù)數(shù)據(jù)等等,而不用關(guān)心當(dāng)前節(jié)點(diǎn)是部門還是人。

操作系統(tǒng)的文件夾與文件

操作系統(tǒng)的文件夾與文件也是典型的樹狀結(jié)構(gòu),為了方便遞歸出文件夾內(nèi)文件數(shù)量或者文件總大小,我們最好設(shè)計(jì)的時(shí)候就將文件夾與文件抽象為文件,這樣每個(gè)節(jié)點(diǎn)都擁有相同的方法添加、刪除、查找子元素,而不需要關(guān)心當(dāng)前節(jié)點(diǎn)是文件夾或是文件。

搭建平臺(tái)的組件與容器

容器與組件的關(guān)系很小,用戶常常認(rèn)為容器也是一種組件,但搭建平臺(tái)實(shí)現(xiàn)時(shí),容器與組件稍有不同,不同之處在于容器可以嵌套子元素,而組件不可以。如果因此搭建平臺(tái)就將組件分為容器與組件,會(huì)導(dǎo)致 API 割裂為兩套,不利于組件開發(fā)者維護(hù)與用戶理解,比較好的設(shè)計(jì)思路是將組件與容器統(tǒng)一看成組件,組件只是一種沒有子元素的特殊容器,這樣組件與容器就可以擁有相同的 API,統(tǒng)一理解與操作了。

意圖解釋

意圖:將對(duì)象組合成樹形結(jié)構(gòu)以表示 “部分 - 整體” 的層次結(jié)構(gòu)。Composite 使得用戶對(duì)單個(gè)對(duì)象和組合對(duì)象的使用具有一致性。

比較好理解,組合是指多個(gè)對(duì)象雖然有一定差異,但共同組合成了一個(gè)樹形結(jié)構(gòu),那么對(duì)象之間就一定存在 “部分 - 整體” 的關(guān)系,組合模式要求我們抽象一個(gè)對(duì)象 Component 作為統(tǒng)一操作模型,葉子結(jié)點(diǎn)與非葉子結(jié)點(diǎn)都實(shí)現(xiàn)了所有功能,即便是沒有子元素的葉子結(jié)點(diǎn),為了強(qiáng)調(diào)透明性,還是具備比如 getChildren 方法,只不過永遠(yuǎn)都返回 null。

結(jié)構(gòu)圖

其中 Component 是組合中對(duì)象聲明接口,一般會(huì)實(shí)現(xiàn)所有公共類的所有接口,還要提供一個(gè)接口管理其子組件。

Leaf 表示葉子結(jié)點(diǎn),沒有子結(jié)點(diǎn),相應(yīng)的 Composite 就是有子結(jié)點(diǎn)的節(jié)點(diǎn)。

可以看到,組合模式就是將樹狀結(jié)構(gòu)中所有節(jié)點(diǎn)統(tǒng)一抽象了,我們不需要關(guān)心葉子結(jié)點(diǎn)與非葉子結(jié)點(diǎn)的差異,而可以通過組合模式的抽象屏蔽掉這些差異,統(tǒng)一處理。

代碼例子

下面例子使用 typescript 編寫。

// 統(tǒng)一的抽象

class Component {

  // 添加子元素

  public add() {}

  // 獲取名稱

  public getName() {}

  // 獲取子元素

  public getChildren() {}

}

// 非葉子結(jié)點(diǎn)

class Composite extends Component {

  public add(component: Component) {

    this.children.push(component)

  }

  public getName() {

    return this.name

  }

  public getChildren() {

    return this.children

  }

}

// 葉子結(jié)點(diǎn)

class Leaf extends Component {

  public add(component: Component) {

    throw Error('葉子結(jié)點(diǎn)無法添加元素')

  }

  public getName() {

    return this.name

  }

  public getChildren() {

    return null

  }

}

最后我們把對(duì)所有節(jié)點(diǎn)的操作都轉(zhuǎn)為 Component 對(duì)象,而不用關(guān)心這個(gè)對(duì)象具體是 Composite 或 Leaf。

弊端

組合模式進(jìn)行了一層抽象,其實(shí)增加了復(fù)雜系統(tǒng)中業(yè)務(wù)復(fù)雜度。如果 Composite 與 Leaf 差異過大,那么統(tǒng)一抽象帶來的理解成本是很高的。

同時(shí),Leaf 不得不實(shí)現(xiàn)一些僅 Composite 存在的空函數(shù),比如 add delete,即便這些方法對(duì)他們是無意義的,此時(shí)可能要進(jìn)行統(tǒng)一的無效或錯(cuò)誤處理,才能使業(yè)務(wù)層真正不用感知他們的區(qū)別,否則 add 可能會(huì)失敗,其本質(zhì)上還是將節(jié)點(diǎn)的區(qū)別暴露給了業(yè)務(wù)層。

讀到這里,這篇“Composite組合模式怎么實(shí)現(xiàn)”文章已經(jīng)介紹完畢,想要掌握這篇文章的知識(shí)點(diǎn)還需要大家自己動(dòng)手實(shí)踐使用過才能領(lǐng)會(huì),如果想了解更多相關(guān)內(nèi)容的文章,歡迎關(guān)注億速云行業(yè)資訊頻道。

向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI