一贬芥、代理模式(Proxy Pattern )
定義:Provide a surrogate or placeholder for another object to control access to it.
(為其他對(duì)象提供一種代理以控制對(duì)這個(gè)對(duì)象的訪問派殷。)
● Subject 抽象主題角色
抽象主題類可以是抽象類也可以是接口,是一個(gè)最普通的業(yè)務(wù)類型定義雌贱,無特殊要
求。
● RealSubject 具體主題角色
也叫做被委托角色、被代理角色禀忆。它才是冤大頭爆惧,是業(yè)務(wù)邏輯的具體執(zhí)行者狸页。
● Proxy 代理主題角色
也叫做委托類、代理類扯再。它負(fù)責(zé)對(duì)真實(shí)角色的應(yīng)用芍耘,把所有抽象主題類定義的方法
限制委托給真實(shí)主題角色實(shí)現(xiàn),并且在真實(shí)主題角色處理完畢前后做預(yù)處理和善后
處理工作熄阻。
普通代理和強(qiáng)制代理:
普通代理就是我們要知道代理的存在斋竞,也就是類似的 GamePlayerProxy 這個(gè)類的
存在,然后才能訪問秃殉;
強(qiáng)制代理則是調(diào)用者直接調(diào)用真實(shí)角色窃页,而不用關(guān)心代理是否存在,其代理的產(chǎn)生
是由真實(shí)角色決定的复濒。
普通代理:
在該模式下脖卖,調(diào)用者只知代理而不用知道真實(shí)的角色是誰,屏蔽了真實(shí)角色的變更
對(duì)高層模塊的影響,真實(shí)的主題角色想怎么修改就怎么修改,對(duì)高層次的模塊沒有
任何的影響绞绒,只要你實(shí)現(xiàn)了接口所對(duì)應(yīng)的方法,該模式非常適合對(duì)擴(kuò)展性要求較高
的場(chǎng)合十籍。
強(qiáng)制代理:
強(qiáng)制代理的概念就是要從真實(shí)角色查找到代理角色,不允許直接訪問真實(shí)角色唇礁。高
層模塊只要調(diào)用 getProxy 就可以訪問真實(shí)角色的所有方法勾栗,它根本就不需要產(chǎn)生
一個(gè)代理出來,代理的管理已經(jīng)由真實(shí)角色自己完成盏筐。
動(dòng)態(tài)代理:
根據(jù)被代理的接口生成所有的方法围俘,也就是說 給定一個(gè)接口,動(dòng)態(tài)代理會(huì)宣稱 “ 我
已經(jīng)實(shí)現(xiàn)該接口下的所有方法了 ” 琢融。
兩條獨(dú)立發(fā)展的線路界牡。動(dòng)態(tài)代理實(shí)現(xiàn)代理的職責(zé),業(yè)務(wù)邏輯 Subject 實(shí)現(xiàn)相關(guān)的邏
輯功能漾抬,兩者之間沒有必然的相互耦合的關(guān)系宿亡。通知 Advice 從另一個(gè)切面切入,
最終在高層模塊也就是 Client 進(jìn)行耦合纳令,完成邏輯的封裝任務(wù)挽荠。
動(dòng)態(tài)代理調(diào)用過程示意圖:
動(dòng)態(tài)代理的意圖:橫切面編程克胳,在不改變我們已有代碼結(jié)構(gòu)的情況下增強(qiáng)或控制對(duì)
象的行為。
首要條件:被代理的類必須要實(shí)現(xiàn)一個(gè)接口圈匆。
二毯欣、原型模式(Prototype Pattern )
定義:Specify the kinds of objects to create using a prototypical instance,and
create new objects by copying this prototype.(用原型實(shí)例指定創(chuàng)建對(duì)象的種類,
并且通過拷貝這些原型創(chuàng)建新的對(duì)象臭脓。)
原型模式通用代碼:
public class PrototypeClass implements Cloneable{
//覆寫父類 Object 方法
@Override
public PrototypeClass clone(){
PrototypeClass prototypeClass = null;
try {
prototypeClass = (PrototypeClass)super.clone();
} catch (CloneNotSupportedException e) {
//異常處理
}
return prototypeClass;
}
}
原型模式實(shí)際上就是實(shí)現(xiàn) Cloneable 接口,重寫 clone ()方法腹忽。
使用原型模式的優(yōu)點(diǎn):
● 性能優(yōu)良
原型模式是在內(nèi)存二進(jìn)制流的拷貝来累,要比直接 new 一個(gè)對(duì)象性能好很多,特別是
要在一個(gè)循環(huán)體內(nèi)產(chǎn)生大量的對(duì)象時(shí)窘奏,原型模式可以更好地體現(xiàn)其優(yōu)點(diǎn)嘹锁。
● 逃避構(gòu)造函數(shù)的約束
這既是它的優(yōu)點(diǎn)也是缺點(diǎn),直接在內(nèi)存中拷貝着裹,構(gòu)造函數(shù)是不會(huì)執(zhí)行的(參見
13.4 節(jié))领猾。
使用場(chǎng)景:
● 資源優(yōu)化場(chǎng)景
類初始化需要消化非常多的資源,這個(gè)資源包括數(shù)據(jù)骇扇、硬件資源等摔竿。
● 性能和安全要求的場(chǎng)景
通過 new 產(chǎn)生一個(gè)對(duì)象需要非常繁瑣的數(shù)據(jù)準(zhǔn)備或訪問權(quán)限,則可以使用原型模
式少孝。
● 一個(gè)對(duì)象多個(gè)修改者的場(chǎng)景
一個(gè)對(duì)象需要提供給其他對(duì)象訪問继低,而且各個(gè)調(diào)用者可能都需要修改其值時(shí),可以
考慮使用原型模式拷貝多個(gè)對(duì)象供調(diào)用者使用稍走。
淺拷貝和深拷貝:
淺拷貝:Object 類提供的方法 clone 只是拷貝本對(duì)象袁翁,其對(duì)象 內(nèi)部的數(shù)組、引用
對(duì)象 等都不拷貝婿脸,還是指向原生對(duì)象的內(nèi)部元素地址粱胜,這種拷貝就叫做 淺拷貝 ,其
他的原始類型比如 int狐树、long焙压、char、string(當(dāng)做是原始類型)等都會(huì)被拷貝抑钟。
注意: 使用原型模式時(shí)冗恨,引用的成員變量必須滿足兩個(gè)條件才不會(huì)被拷貝:一是
類的成員變量 ,而不是方法內(nèi)變量味赃;二是必須是一個(gè) 可變的引用對(duì)象 掀抹,而不是一個(gè)
原始類型或不可變對(duì)象。
深拷貝:對(duì)私有的類變量進(jìn)行獨(dú)立的拷貝
如:thing.arrayList = (ArrayList<String>)this.arrayList.clone();
kx33389,加她就能免費(fèi)領(lǐng)取分布式心俗、微服務(wù)傲武、源碼分析蓉驹、性能優(yōu)化、高并發(fā)高可用等技術(shù)的資料
三揪利、中介者模式
定義:Define an object that encapsulates how a set of objects interact.Mediator
promotes loose coupling by keeping objects from referring to each other
explicitly,and it lets you vary their interaction independently.(用一個(gè)中介對(duì)象封裝
一系列的對(duì)象交互态兴,中介者使各對(duì)象不需要顯示地相互作用,從而使其耦合松散疟位,
而且可以獨(dú)立地改變它們之間的交互瞻润。)
● Mediator 抽象中介者角色
抽象中介者角色定義統(tǒng)一的接口,用于各同事角色之間的通信甜刻。
● Concrete Mediator 具體中介者角色
具體中介者角色通過協(xié)調(diào)各同事角色實(shí)現(xiàn)協(xié)作行為绍撞,因此它必須依賴于各個(gè)同事角
色。
● Colleague 同事角色
每一個(gè)同事角色都知道中介者角色得院,而且與其他的同事角色通信的時(shí)候傻铣,一定要通
過中介者角色協(xié)作。每個(gè)同事類的行為分為兩種:一種是同事本身的行為祥绞,比如改
變對(duì)象本身的狀態(tài)非洲,處理自己的行為等,這種行為叫做自發(fā)行為(Self-
Method)蜕径,與其他的同事類或中介者沒有任何的依賴两踏;第二種是必須依賴中介者
才能完成的行為,叫做依賴方法(Dep-Method)兜喻。
通用抽象中介者代碼:
public abstract class Mediator {
//定義同事類
protected ConcreteColleague1 c1;
protected ConcreteColleague2 c2;
//通過 getter/setter 方法把同事類注入進(jìn)來
public ConcreteColleague1 getC1() {
return c1;
}
public void setC1(ConcreteColleague1 c1) {
this.c1 = c1;
}
public ConcreteColleague2 getC2() {
return c2;
}
public void setC2(ConcreteColleague2 c2) {
this.c2 = c2;
}
//中介者模式的業(yè)務(wù)邏輯
public abstract void doSomething1();
public abstract void doSomething2();
}
ps :使用同事類注入而不使用抽象注入的原因是因?yàn)槌橄箢愔胁痪哂忻總€(gè)同事類
必須要完成的方法缆瓣。即每個(gè)同事類中的方法各不相同。
問:為什么同事類要使用構(gòu)造函數(shù)注入中介者虹统,而中介者使用 getter/setter 方式注
入同事類呢弓坞?
這是因?yàn)橥骂惐仨氂兄薪檎撸薪檎邊s可以只有部分同事類车荔。
使用場(chǎng)景:
中介者模式適用于多個(gè)對(duì)象之間緊密耦合的情況渡冻,緊密耦合的標(biāo)準(zhǔn)是:在類圖中出
現(xiàn)了蜘蛛網(wǎng)狀結(jié)構(gòu),即每個(gè)類都與其他的類有直接的聯(lián)系忧便。
四族吻、命令模式
定義:Encapsulate a request as an object,thereby letting you parameterize clients
with different requests,queue or log requests,and support undoable operations.
(將一個(gè)請(qǐng)求封裝成一個(gè)對(duì)象,從而讓你使用不同的請(qǐng)求把客戶端參數(shù)化珠增,對(duì)請(qǐng)求
排隊(duì)或者記錄請(qǐng)求日志超歌,可以提供命令的撤銷和恢復(fù)功能。)
● Receive 接收者角色
該角色就是干活的角色蒂教,命令傳遞到這里是應(yīng)該被執(zhí)行的巍举,具體到我們上面的例子
中就是 Group 的三個(gè)實(shí)現(xiàn)類(需求組,美工組凝垛,代碼組)懊悯。
● Command 命令角色
需要執(zhí)行的所有命令都在這里聲明蜓谋。
● Invoker 調(diào)用者角色
接收到命令,并執(zhí)行命令炭分。在例子中桃焕,我(項(xiàng)目經(jīng)理)就是這個(gè)角色。
使用場(chǎng)景:
認(rèn)為是命令的地方就可以采用命令模式捧毛,例如观堂,在 GUI 開發(fā)中,一個(gè)按鈕的點(diǎn)擊
是一個(gè)命令呀忧,可以采用命令模式师痕;模擬 DOS 命令的時(shí)候,當(dāng)然也要采用命令模
式荐虐;觸發(fā)-反饋機(jī)制的處理等。