元ネタ → ochococo/Design-Patterns-In-Swift
クラス図
図の引用元:Wikipedia: Adapter パターン
概要
The adapter pattern is used to provide a link between two otherwise incompatible types by wrapping the "adaptee" with a class that supports the interface required by the client.
Adapterパターンは、クライアントが必要とするインターフェースをサポートするAddapterクラスを用意してAdapteeをラップすることにより、2つの互換性のないタイプ間のリンクを提供するために使用されます。
サンプルコード
// Target
protocol NewDeathStarSuperlaserAiming {
// requiredMethod() propertyだがgetterメソッドという扱い
var angleV: Double { get }
var angleH: Double { get }
}
// Adaptee
struct OldDeathStarSuperlaserTarget {
// oldMethod() propertyだがgetterメソッドという扱い
let angleHorizontal: Float
let angleVertical : Float
init(angleHorizontal: Float, angleVertical: Float) {
self.angleHorizontal = angleHorizontal
self.angleVertical = angleVertical
}
}
// Adapter
struct NewDeathStarSuperlaserTarget: NewDeathStarSuperlaserAiming {
// adaptee: Adaptee
private let target: OldDeathStarSuperlaserTarget
// requiredMethod(): this.adaptee.oldMethod()
// Targetに準拠した形式でAdapteeからの戻りをラップする
var angleV: Double {
return Double(target.angleVertical)
}
var angleH: Double {
return Double(target.angleHorizontal)
}
init(_ target: OldDeathStarSuperlaserTarget) {
self.target = target
}
}
// usage //
let target = OldDeathStarSuperlaserTarget(angleHorizontal: 14.0, angleVertical: 12.0)
let newFormat = NewDeathStarSuperlaserTarget(target)
newFormat.angleH
newFormat.angleV
クラス図との対応
サンプルコード | クラス図 |
---|---|
NewDeathStarSuperlaserAiming | Target |
angleV, angleH | requiredMethod() |
サンプルコード | クラス図 |
---|---|
OldDeathStarSuperlaserTarget | Adaptee |
angleHorizontal, angleVertical | oldMethod() |
サンプルコード | クラス図 |
---|---|
NewDeathStarSuperlaserTarget | Adapter |
target | adaptee: Adaptee |
angleV, angleH | requiredMethod() #this.adaptee.oldMethod() |
考察
Adapteeは既存の何らかのクラス。それ自体には変更を加えずにAdapterを用意してラップすることでクライアントが使用できるようにする。TargetはAdapteeから必要な機能をラップする具体的なインタフェースを定義する。ここでは、OldDeathStarSuperlaserTargetのFloat
を返すメソッド(get
プロパティ)をインタフェース(protocol
)で抽出して、Double
を返すようにラップしている。インタフェースを抽出して定義しているのは、Double
を返す形式で、他のクラスと同等に、OldDeathStarSuperlaserTargetの機能を取り込みたいためである。Targetに準拠させることでOldDeathStarSuperlaserTarget以外にも互換性のない様々なクラスを同等に使用することが可能になる。