【オブジェクト指向のこころ】8章 カプセル化

デザインパターンとともに学ぶオブジェクト指向のこころ」の学習記録。
「第8章 視野を広げる」のまとめ。


カプセル化とは

カプセル化とは、「あらゆるものを隠蔽すること」であると考えるべき。
データの隠蔽はカプセル化の1つの側面でしかない。
データ以外にも、実装や派生クラスを隠蔽できる。
つまり、型を隠蔽、型をカプセル化できるということが重要。

GoFカプセル化について言及している場合、ほとんどは型のカプセル化を意味している。

流動的要素のカプセル化

「流動的な要素を見つけ出し、それをカプセル化する。」
これは多くのデザインパターンのテーマになっている。

流動的なクラスの抽象クラスやインタフェース型の参照を、使用するクラスに保持(集約)することで、流動的な振る舞いを隠蔽する。
これは、オブジェクト間にレイヤを作成している、ということ。
これにより他のレイヤに影響を与えることなくあるレイアを修正できるようにする。

動物オブジェクトを考える。
動物は種類毎に移動方法と食性(肉食か草食か)が異なっている。

  • ワシ(飛翔する肉食動物)
  • ライオン(歩行する肉食動物)
  • ツバメ(飛翔する草食動物)
  • 牛(歩行する草食動物)

良くないアプローチ

  • オブジェクトにどちらの移動手段が有効か、どちらの食性が有効かという情報を格納するメンバを用意しswitchする。
    • 流動的要素が増えるにつれ凝縮度は低下する。switchが増え、コードが理解しにくくなっていく。
  • Animalクラスを継承した2つのクラスを作り、一方を歩行用、もう一方を飛翔用とする
    • 特殊ケース毎に継承することで、クラス数の爆発を招くことになる。
    • 歩行と飛翔を行う動物はどうするか?

良いアプローチ

適切な移動方法を定義したAnimalMovement(動物の移動手段)オブジェクトをAnimalクラスに保持させる。

本書の例は以下。
http://www.plantuml.com/plantuml/png/TOsn2i9044Jx_OgjXGDhiKWQmSBAmdgJB7XaznBkDaAC_hkW5uGJotaplAcIKRH91LBlmqYH55kXb6gpw9l9-DWEuUplZ5ku-ewHTRGPbRNXc03UOwo3Ln9SmA7Ef-76oi5s6QyPddbUS5pAvY3pBxoGz1-QtpQkF2Yy-uTpN-EVTbL3nQ6RL5u0

他の本では以下の例があった。
http://www.plantuml.com/plantuml/png/TOqn2y9038Nt_8hCGekpEBIBuE3au9os4OzUqdAN2bNxtnMjY2UE-LxUzufe56mG3x5rsbCWmTfJZALPSDLWlAqxtRiBun9Ehc5awMr4OQauH83dCvRgX3nU8KCPTzsPXTLMCtxVC04uDGv7gZd97jNfMxRnuoyya6zVT5vSPEb8ubtVylnZ_9VEQYXOcq7y7G00