每日Android源碼設(shè)計(jì)模式之-15、訪問者模式

訪問者模式是23種設(shè)計(jì)模式中最復(fù)雜的一個(gè),使用頻率并不高,一般不需要用,如果你一旦需要使用,那就是真的需要了。

它是一種將數(shù)據(jù)操作和數(shù)據(jù)結(jié)構(gòu)分離的設(shè)計(jì)模式。


定義

封裝一些作用于某種數(shù)據(jù)結(jié)構(gòu)中的各元素操作,它可以在不改變這個(gè)數(shù)據(jù)結(jié)構(gòu)的前提下定義作用于這些元素的新的操作。


使用場(chǎng)景

1.對(duì)象結(jié)構(gòu)比較穩(wěn)定,但經(jīng)常需要再次對(duì)象結(jié)構(gòu)上定義新的操作。

2.需要對(duì)一個(gè)對(duì)象結(jié)構(gòu)中的對(duì)象進(jìn)行很多不同的并且不相關(guān)的操作,而需要避免這些操作“污染”這些對(duì)象的類,也不希望在增加新操作時(shí)修改這些類。


來看一個(gè)實(shí)現(xiàn)

企業(yè)業(yè)績考核,有工程師和經(jīng)理兩種職工,老板有CEO和CTO,CTO只關(guān)心工程師的代碼數(shù)量、經(jīng)理的產(chǎn)品數(shù)量。CEO關(guān)心工程師和經(jīng)理的KPI。

于是我們定一個(gè)staff員工基類,有一個(gè)抽象方法accept(Visitor visitor),他有兩個(gè)子類Engineer和Mnager,他們實(shí)現(xiàn)了accept(Visitor visitor)方法,并且在accept方法中調(diào)用visitor.visit(this);

而Visitor類中的visit方法有兩個(gè)重載一個(gè)是visit(Engineer)另一個(gè)是visit(Manager),而Visitor類兩個(gè)子類CTO和CEO兩個(gè)類在實(shí)現(xiàn)這兩個(gè)visit方法的時(shí)候去根據(jù)需求來訪問不同的數(shù)據(jù)就行了。

最后有一個(gè)中的報(bào)表類,類里面用例如List存儲(chǔ)了所有員工的資料,然后有一個(gè)showReport(Visitor visitor)方法,方法里面遍歷所有員工accpet并傳入visitor。

每一個(gè)對(duì)象的accept(Visitor)調(diào)用了visitor.visit(this)方法,visitor中又根據(jù)傳過來的this判斷是哪個(gè)對(duì)象去獲取需要的數(shù)據(jù)。

這就是一個(gè)訪問者模式的簡(jiǎn)單實(shí)現(xiàn),其實(shí)也還是不難的。


Android源碼中的訪問者模式

編譯時(shí)注解依賴于APT(Annotation Processing Tools)實(shí)現(xiàn),在編譯器會(huì)自己生成相關(guān)的java類。

注解可以指定作用于哪種元素上, ?比如:

PackageElement,包元素

TypeElement,類型元素

ExecutableElement,可執(zhí)行元素

VariableElement,變量元素

TypeParameterElement,類型參數(shù)元素


Element基類里面有一個(gè)accept(ElementVisitor<R,p> v,P p)方法

ElementVisitor里面又根據(jù)不同的元素類型重載很很多visit方法。

比如類型元素訪問者 里面是visitType(TypeElement e,P p)方法,然后里面做了這種類型元素需要的操作。

顯然這就是一個(gè)訪問者模式。


優(yōu)點(diǎn):

1.角色職責(zé)分離,符合單一職責(zé)原則。

2.具有優(yōu)秀的擴(kuò)展性。

3.使得數(shù)據(jù)結(jié)構(gòu)和作用于結(jié)構(gòu)上的操作解耦,使得操作集合可以獨(dú)立變化。

4.靈活性。


缺點(diǎn):

1.具體元素對(duì)訪問者公布細(xì)節(jié),違反了迪米特原則

2.具體元素變更時(shí),修改成本大

3.違反了依賴倒置原則,為了區(qū)別對(duì)待而依賴了具體類,而不是依賴抽象。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 1 場(chǎng)景問題# 1.1 擴(kuò)展客戶管理的功能## 考慮這樣一個(gè)應(yīng)用:擴(kuò)展客戶管理的功能。 既然是擴(kuò)展功能,那么肯定是...
    七寸知架構(gòu)閱讀 3,044評(píng)論 1 58
  • 訪問者模式是一種將數(shù)據(jù)操作與數(shù)據(jù)結(jié)構(gòu)分離的設(shè)計(jì)模式。確實(shí)是我目前為止見過的最復(fù)雜的了。 博客地址 訪問者模式的思想...
    喵了個(gè)嗚s閱讀 544評(píng)論 0 0
  • 1. Java基礎(chǔ)部分 基礎(chǔ)部分的順序:基本語法,類相關(guān)的語法,內(nèi)部類的語法,繼承相關(guān)的語法,異常的語法,線程的語...
    子非魚_t_閱讀 34,767評(píng)論 18 399
  • 每個(gè)人都會(huì)有不愿意分享的煩惱和苦痛,因?yàn)橐徽f出來,感覺似乎又加重了一些。 或許就讓它一點(diǎn)點(diǎn)的融化在時(shí)間里,直至爛去...
    亦喬靈兒閱讀 197評(píng)論 0 0
  • 昨天去給閨蜜幫忙,吃飯的時(shí)候我對(duì)她抱怨道:我媽和小姨在催我畢業(yè)就結(jié)婚,但是這明顯不可能嘛! 瑤說:我小姨一直在慫恿...
    貓咪家的小豆豆閱讀 741評(píng)論 0 5

友情鏈接更多精彩內(nèi)容