凝縮度に関して
凝縮度なんて情報処理試験勉強のための用語だと思ってました。用語を覚える必要はないですがこれらの根底にある考え方を理解するとソースコードの実装が捗りそうです。
凝縮度が低いとモジュールのAPIに一貫性がないため再利用性が低くなるんですよね。凝縮度と似たような概念に結合度があるのですが、凝縮度は1つのモジュール内部の話で、結合度はモジュール間の話です。つまりモジュール設計に関しては凝縮度をIF設計に関しては結合度を意識するとよいと。
前提
ここでは「システムは複数の機能からなり1つの機能は複数の処理からなる」ことを前提にしている。これらの機能・処理に対してモジュール化の切り口をどうするかを議論している。
- 機能の例:データベースの管理
- 処理の例:データベースと接続・SQL文の実行・結果の取得・結果の解析・データベースと切断
低い凝縮度
ありがちなUtilityクラスは凝縮度が低かったのか!以下の2つは避けるべき。
偶発的凝集
- 1つのモジュール内に、無作為に集められた機能・処理が存在する。モジュール内の各部分には関連性はない。
- 例えば各モジュールの共通関数を集めたモジュールとか(ざらにありそうだけど)。
- 複数機能が混在しているため再利用性がない。
論理的凝集
- 関連する複数の機能を集めたモジュール。
- 呼び出し元は(if分やcase文に用いる)呼び出し時にフラグを指定して利用する機能を指定する。
- 呼び出し元がモジュール内部のロジックを知る必要がありモジュールがブラックボックス化されていない。
- イベントによる処理の振り分け制御など。
- 複数機能が混在しているため再利用性がない。
中程度の凝縮度
時間的凝集(一時的凝縮)
- あるときにまとめて実行する処理をまとめたモジュール。
- 例えば初期化処理だけを集めたモジュール、終了処理だけを集めたモジュールなど。
- モジュール内の処理間は複数の機能にまたがっている。
- 複数機能が混在しているため再利用性がない。
手続き的凝集
- (扱うデータは異なるが)関連する複数の機能を集めたモジュール。
- GoFのFacade(窓口)パターンに相当。
高い凝縮度
- 機能的凝縮が理想だが常に実現できるとは限らない。とりあえず自分が設計するときはこの高い凝縮度を意識しようと思います。
- 1モジュール1機能ではあるが、1機能1モジュールとは限らないことに注意。
通信的凝縮
- モジュール内には1つの機能のみが存在する。
- 特定のデータを扱う処理の集まりだが順番は関係のない部分を集めたモジュール。
- 例えば同種のレコードの情報を操作するルーチンを集めたモジュールなど。
- 順番が関係がない=モジュールの呼び出し元で順番を制御するロジックを実装する必要がある。
逐次的凝集
- モジュール内には1つの機能のみが存在する。
- 特定のデータを扱う処理の集まりでかつ順番に関係がある部分を集めたモジュール。
- ある部分の出力が別の部分の入力となるような部分を集めたモジュール。
- 例えば全体としてあるファイルを読み込んで処理をするモジュール。
- 順番が関係がある=モジュールの呼び出し元は呼び出すだけでよい。
機能的凝集
- モジュール内には1つの機能のみが存在する。
- 1機能1モジュール。
- ある特定の機能(例えば角度のサインを計算するモジュール・テーブルのI/Oに特価したDAOパターン)に特化したモジュール
感想
- 基本的に1モジュール1機能(当然だけど)にしておけば最低限の凝縮度は担保される。