以最簡(jiǎn)單的module學(xué)習(xí)設(shè)計(jì)模式打肝,理解最重要
設(shè)計(jì)模式持續(xù)更新中:http://www.reibang.com/p/e3c25095c31f
持續(xù)更新中
適配器模式:將一個(gè)類的接口轉(zhuǎn)換成客戶希望的另外一個(gè)接口。適配器模式使得原本由于接口不兼容而不能一起工作的那些類可以一起工作。
適配器模式的三個(gè)特點(diǎn):
- 1、 適配器對(duì)象實(shí)現(xiàn)原有接口
- 2、 適配器對(duì)象組合一個(gè)實(shí)現(xiàn)新接口的對(duì)象(這個(gè)對(duì)象也可以不實(shí)現(xiàn)一個(gè)接口洞翩,只是一個(gè)單純的對(duì)象)
- 3、 對(duì)適配器原有接口方法的調(diào)用被委托給新接口的實(shí)例的特定方法
前言
代碼實(shí)現(xiàn)倉(cāng)庫(kù): https://github.com/AnyMarvel/desigPattern
適配器模式焰望,簡(jiǎn)言之骚亿,即定義一個(gè)包裝類,用于包裝不兼容接口的對(duì)象
包裝類 = 適配器Adapter熊赖;
被包裝對(duì)象 = 適配者Adaptee = 被適配的類
主要解決:主要解決在軟件系統(tǒng)中来屠,常常要將一些"現(xiàn)存的對(duì)象"放到新的環(huán)境中,而新環(huán)境要求的接口是現(xiàn)對(duì)象不能滿足的震鹉。
何時(shí)使用:
- 1俱笛、系統(tǒng)需要使用現(xiàn)有的類,而此類的接口不符合系統(tǒng)的需要足陨。
- 2嫂粟、想要建立一個(gè)可以重復(fù)使用的類,用于與一些彼此之間沒(méi)有太大關(guān)聯(lián)的一些類墨缘,包括一些可能在將來(lái)引進(jìn)的類一起工作星虹,這些源類不一定有一致的接口零抬。
- 3、通過(guò)接口轉(zhuǎn)換宽涌,將一個(gè)類插入另一個(gè)類系中平夜。(比如老虎和飛禽,現(xiàn)在多了一個(gè)飛虎卸亮,在不增加實(shí)體的需求下忽妒,增加一個(gè)適配器,在里面包容一個(gè)虎對(duì)象兼贸,實(shí)現(xiàn)飛的接口段直。)
白話適配器模式
使用電源插座的例子來(lái)描述適配器模式,假設(shè)以下場(chǎng)景:
場(chǎng)景:國(guó)標(biāo)(國(guó)內(nèi)標(biāo)準(zhǔn))插座為3個(gè)孔溶诞,德標(biāo)準(zhǔn)(德國(guó)標(biāo)準(zhǔn))插座為2個(gè)孔
問(wèn)題:一國(guó)內(nèi)游客去德國(guó)旅游鸯檬,拿著國(guó)標(biāo)的充電器(3個(gè)孔)如何使用德標(biāo)的插孔(2個(gè)孔)
解決辦法:電源轉(zhuǎn)化適配器
UML類圖:
定義國(guó)標(biāo)接口
/**
* 國(guó)標(biāo)接口
*/
interface GBSocketInterface {
/**
* 使用三項(xiàng)扁頭的插口供電
*/
fun powerWithThreeFlat()
}
實(shí)現(xiàn)國(guó)標(biāo)接口的中國(guó)插座
/**
* 中國(guó)插座
*/
class GBSocket : GBSocketInterface {
override fun powerWithThreeFlat() {
println("使用三項(xiàng)扁頭插孔供電")
}
}
定義德標(biāo)接口
/**
* 德標(biāo)接口
*/
interface DBSocketInterface {
/**
* 使用兩項(xiàng)圓頭的插口供電
*/
fun powerWithTwoRound()
}
實(shí)現(xiàn)德標(biāo)接口的德國(guó)插座
/**
* 德國(guó)插座
*/
class DBSocket : DBSocketInterface {
override fun powerWithTwoRound() {
println("使用兩項(xiàng)圓頭的插孔供電")
}
}
實(shí)現(xiàn)德國(guó)賓館,使用德國(guó)插座
/**
* 德國(guó)賓館
*/
internal class Hotel {
/**
* 旅館中有一個(gè)德標(biāo)的插口
*/
private var dbSocket: DBSocketInterface? = null
/**
* 德國(guó)賓館設(shè)置
*
* @param dbSocket
*/
fun setDbSocket(dbSocket: DBSocketInterface) {
this.dbSocket = dbSocket
}
/**
* 旅館中有一個(gè)充電的功能
*/
fun charge() {
//使用德標(biāo)插口充電
dbSocket!!.powerWithTwoRound()
}
}
創(chuàng)建適配器螺垢,適配器需要將國(guó)標(biāo)接口轉(zhuǎn)換為德標(biāo)接口喧务,必須滿足以下條件:
1 必須符合德國(guó)標(biāo)準(zhǔn)的接口,否則的話還是沒(méi)辦法插到德國(guó)插座中枉圃;
2 在調(diào)用上面實(shí)現(xiàn)的德標(biāo)接口進(jìn)行充電時(shí)功茴,提供一種機(jī)制,將這個(gè)調(diào)用轉(zhuǎn)到對(duì)國(guó)標(biāo)接口的調(diào)用 孽亲。
這就要求:
1 適配器必須實(shí)現(xiàn)原有的舊的接口
2 適配器對(duì)象中持有對(duì)新接口的引用坎穿,當(dāng)調(diào)用舊接口時(shí),將這個(gè)調(diào)用委托給實(shí)現(xiàn)新接口的對(duì)象來(lái)處理墨林,也就是在適配器對(duì)象中組合一個(gè)新接口赁酝。
/**
* 適配器實(shí)現(xiàn)德標(biāo)接口
*/
class SocketAdapter : DBSocketInterface {
/**
* 組合新接口
*/
private var gbSocket: GBSocketInterface
/**
* 在創(chuàng)建適配器對(duì)象時(shí),必須傳入一個(gè)新接口的實(shí)現(xiàn)類
*
* @param gbSocket 國(guó)標(biāo)接口
*/
internal constructor(gbSocket: GBSocketInterface) {
this.gbSocket = gbSocket
}
/**
* 將對(duì)舊接口的調(diào)用適配到新接口
*/
override fun powerWithTwoRound() {
gbSocket.powerWithThreeFlat()
}
}
測(cè)試代碼:
object AdapterTest {
@JvmStatic
fun main(args: Array<String>) {
/**
* 初始化一個(gè)中國(guó)插座對(duì)象旭等, 用一個(gè)國(guó)標(biāo)接口引用它
*/
val gbSocket = GBSocket()
/**
* 創(chuàng)建一個(gè)旅館對(duì)象
*/
val hotel = Hotel()
/**
* 創(chuàng)建適配器,使國(guó)標(biāo)接口適配國(guó)標(biāo)接口
*/
val socketAdapter = SocketAdapter(gbSocket)
/**
* 設(shè)置插座
*/
hotel.setDbSocket(socketAdapter)
/**
* 在旅館中給手機(jī)充電
*/
hotel.charge()
}
}
運(yùn)行結(jié)果:
如果你對(duì)此感興趣酌呆,可訂閱(感謝你的關(guān)注):