関数型プログラミングを学ぶといらないやつ見えてくるよねって話
生成に関するパターン
構造に関するパターン
振る舞いに関するパターン
これらのパターンが現在の環境でホントに要るかを独断で判断します。
使う
Abstract Factory
Factory Method
まとめてFactoryでいいと思う。
オブジェクトの生成で、クラス指定するのを切り替え可能にするパターン。
高階関数が使える最近の言語ならこんな枠組み用意しなくても、
オブジェクト返す関数を登録して使うようにしたら済む話。
フレームワークとかでは使われてるので覚えてはおきたい。
Singleton
あまり良いパターンではないと言われてると思うが、そこそこ使うと思う
使わない
Builder
メソッドチェーンで選択的に初期化できる。
最近の言語では、初期化子で設定柔軟にできるので不要。
フレームワークとかでは使われてるので覚えてはおきたい。
Prototype(Clone)
Clone()の実装の仕方。
言語標準でIClonable的なインターフェイスが用意されてることが多いから、
自分でインターフェイスを作成することはない。
使う
Adapter
Facade
Proxy
微妙に目的が違うだけで、構造としては同じ。
何かと何かの間に挟まって仕事する。
AdapterはAをBが使いたい形に変換。
FacadeはAが複雑なのをBにシンプルな形にする。
Proxyは間に層を設けてふるまいを切り替える。アクセス保護、キャッシュ、モック。
変更したいものを直接変更せずに、中間層を用意しようという哲学だけ学べば、
それぞれのパターンを覚えなくてもつぶしが利く。
Bridge
委譲によって実装を別クラスで行い、
そのクラスの持ち方を継承で拡張してく。IPhone
,IWatch
,ICalendar
みたいに、実装の詳細を委譲させて、PDA { IWatch watch, ICalendar calendar }
,SmartPhone extend PDA { IPhone phone }
みたいに持たせるものを定義するクラスを継承で拡張させてく。
上で書いた例のように、継承だとうまく表現できない関係が多いと思う。
継承よりも委譲と言われてるから、持たせる側のクラスの継承関係が便利には思えない。
実装の詳細を委譲させてるという考え方だけ採用すべき。
そっちにはパターン名ついてないんのが困る。
Composite
Tree-Leaf構造。ファイルとディレクトリのような関係。
再帰的に処理可能。自身の型のコレクションを持つ。
Tree-Leaf構造が必要になったらお世話になると思う。
Decorator
インターフェイスを継承しつつ、プロパティに持つ。
インターフェイスに定義されたメソッド呼ばれたら、
プロパティに持ったベースオブジェクトの同名メソッドを呼びつつ、
自前の拡張を行って、呼び元に返す。
マトリョーシカのように機能の拡張ができる。
使わない
使う
Strategy
実装の詳細を切り替え可能にするパターン。
良いパターンではあるが、高階関数が使える最近の言語では高階関数で置き換え可能。
State
状態を表す具象クラスを状態ごとにextendしてメソッドのふるまいを変える。
状態遷移図と対応付けられるので便利。
Observer
通知のベストプラクティス。
ライブラリとかについてきて、自分で実装することないかもだが覚えておきたい。
Command
Undo/Redo のベストプラクティス。
使わない寄りではあるが、一応使うに置いた。
使わない
Mediator
呼び出しが交差するのを仲介する。
できれば構造設計見直して回避すべき。
ゲームのオブジェクトみたいに相互作用する構造だと確かに必要。
Iterator
言語で実装されてるから自分で実装することない。
Visitor
Template Method
元の構造の中の処理部分を変更可能にするパターン。
高階関数が使える最近の言語では不要。
Memento
Interpreter
Chain of Responsibility
ユースケースが限定的で使うことない
デザインパターン紹介 —GoF以外のパターンを紹介します— 結城浩 から抜粋。
Null Object
絶対覚えるべき。呼出し側のnullチェックがいらなくなってコードがすっきりする。
何も起こらないことが保証できるし最高。
Balking
busyフラグで動作中は無視する。ダブルクリック防止でよく使った。
Immutable
最近値オブジェクトとかで不変オブジェクトが使われたりで注目。
Hook Opepation
処理の中に任意の処理をフックさせるポイントを用意する。
Emacsでは当たり前のパターンだけど、デザインパターンとして認識してなかった。
Before/After
何かの処理の前後に処理をさせたい構造をテンプレ化。
Emacsだとwith-temp-bufferみたいな関数の機能に似てる。
関数型言語とかEmacs lispとかやってることで、新たな気づきがあった。