天使の取り分

ソフトウェア開発に関するよもやま

Clean Architectureを読む(3)

4章 STRUCTURED PROGRAMMING

4章は構造化プログラミングについて述べられています。
ソフトウェアの複雑さに立ち向かう方法として、ダイクストラは数学的証明の手法を取り入れようとしました。大きな問題を小さな問題に分割して一つ一つ解決していく、いわゆるdivide and conquerのアプローチです。ところが、プログラムにgoto文があると分解することが難しくなります。そこでダイクストラgoto文は有害であると主張し、10年に渡る論争があったそうです。
結果的にgoto文はプログラミング言語から排除され、無秩序な制御の移転は許されなくなりました。ただし、ダイクストラの目的であった、数学的証明をプログラミングに取り込むことは実現されませんでした。結局のところ、ソフトウェアは数学というよりむしろ科学であると筆者は考えています。科学の法則は数学のように正しさを証明することはできず、実験や観測によって誤っていることを示す(falsify)ことしかできない、ソフトウェアもテストによって誤りを発見することはできても正しいことを証明することは不可能なのだと。テストで誤りを発見するためには、テストができるように小さな関数にプログラムを分割する必要があり、それが構造化プログラミングの手法ということです。
というわけで、4章で構造化プログラミングはdirect transer of controlに規律を与えると書かれていましたが、これはgoto文を許容せず、小さな単位に分解可能な構造をソフトウェアにもたらすものであると理解しました。

5章 OBJECT-ORIENTED PROGRAMMING

OOの定義はいろいろありますが、よく言われる以下の3つの特徴があります。

  1. カプセル化 (encapsulation)
  2. 継承(inheritance)
  3. ポリモーフィズム(多態性polymorphism)

それぞれについて、以下のように述べられています。

  • カプセル化はCのヘッダファイルでも実現できていたし、むしろそちらの方が情報隠蔽できている。従ってカプセル化はOOの決定的要素ではない。
  • 継承はOO以前でも実現する技法が存在した。ただしOOによって便利になった。
  • これもOO以前でも実現できたが、関数の実体を指すポインタを自前で管理する必要があり、危険だった。OOによって安全に実現できるようになった。

ポリモーフィズムがOOの中で最も重要な特徴であると筆者は主張しています。なぜ重要かというと、それによって依存関係の逆転(dependency inversion)が可能となるからです。
通常、制御の流れとソースコードの依存関係の方向は同じになります。上位レベルのプログラムが使用するプログラムはimportなどで指定するため、上位→下位へのソースの依存関係が生じます。ところがOOのインタフェース(あるいは抽象クラス)を使用すれば、ソースコード上では下位のプログラムが上位のプログラム(インタフェース)に依存するように反転できるのです。 ポリモーフィズムあらゆるソースコードの依存性の方向を完全に制御する能力を与えてくれるのだと言います。
この能力によってプラグインアーキテクチャを構築することが可能となります。ハイレベルやポリシーを表すビジネスルール(あるいはドメインロジックと言ってよいかもしれません)がローレベルな詳細であるUIやDBに依存するのではなく、その逆であるアーキテクチャ(ビジネスルールが主役のアーキテクチャ)であれば、UIやDBを必要に組み替えることすら可能であるということです。

ということで、3章で述べられていた、OOはindirect transfer of controlに規律を与えるというのは、(関数ポインタを自前で管理する危険なやり方ではなく)安全にポリモーフィズムを実現する能力こそがOOの大きな力であるということになります。

5章はClean Architecture って何?という命題に対する答えのヒントとなる重要な章のようですので、しっかり理解して先の章へ進んでいきたいと思います。