Application Application Design 勉強会 #2
Application Design 勉強会 #2 Wed Jun 26Kazuki Chigita
View Slide
第7章 アジャイル設計
アジャイル開発の考え - アジャイル開発での全体像はソフトウェアと共に 展開していく. - 先を見越してデータベースの設計はしないし,将来の要求に時間を掛けない. - 各イテレーションで「今」を最良の構造にし,常に「今」と同じレベルの品質を保つ.
アジャイル設計ってなに? - アジャイル開発で用いる 設計 手法 - つまり,どういうソースコードであるべきかが 「設計」だ (著者談) - なぜアジャイル設計をするのか? - ソフトウェアはアジャイル開発のイテレーションを 通して変化し続ける. - これに追従して設計をしないと「悪臭」がする. - 「悪臭」がすると,保守がしづらくなったり,機能追加に多大な工数がかかったりする. UMLダイアグラムのような抽象的に表現する技法での 設計ではなく,これを具体化した ソースコード自身のこと. だから,設計をしなければならない.
悪臭の例 1. 硬さ 変更しにくいシステム.1つの変更のためにそれと依存関係に あるモジュールが芋づる式に変更点があらわれること. 2. もろさ 1つの変更によって,概念的に関連のない箇所までもが壊れて しまうシステム. 3. 移植性のなさ 他のシステムで利用価値のある部分をモジュールとして切り出すことが難しい状態. 4. 扱いにくさ ソフトウェアの扱いにくさ,開発環境の扱いにくさ. 5. 不必要な複雑さ 設計時に不必要な仕様を取り込んでいる(アジャイル開発の考えに反している) 6. 不必要な繰り返し 別モジュールからコピペしてきたものを含んでいる. 抽象化すべき. 7. 不透明さ わかりにくいモジュールが存在する状態.
何がソフトウェアを腐敗させるのか? - 仕様変更に追従できなくなったときにソフトウェアが 腐る. - 仕様変更に追従できない→設計に問題がある→ アジャイル開発に耐えうる設計やプラクティスを実践するべき - アジャイルチームはソフトウェアの腐敗を許すな. - じゃあどうすれば?→クリーンな設計やプラクティスを実践するべき. - クリーンな設計やプラクティスを以降の章で紹介.
第8章 単一責任の原則(SRP)
単一責任の原則 (SRP : Single Responsibility Principle) - SOLID原則の一角を成す. - 日本語での説明 - クラスを変更する理由は2つ以上存在してはならない - 本には1つ以上と書いてあるけど,多分違う.
Rectangleクラスの例 - Geometry applicationが演算処理のためにRectangleクラスを参照する. - Graphical ApplicationはGUIへの描画のためにRectangleクラスを参照する. GeometryApplicationGUIGraphicalApplicationRectangle+draw()+area(): double
SRP違反の改善 - この状況下でのRectangleの役割 1. 数学的なモデルを提供する役割 2. GUIで四角形を塗りつぶす役割 - 悪臭シリーズでいうところの扱いにくさ - Geometry applicationが不必要にGUIを含む構図に なっている. - GUI都合で表示するものが変わったときに無関係なGeometryApplicationも変更の必要が生まれる. - 解決策は,演算部分を切り出す(抽象化してinterfaceを切り出す操作と言える) GeometryApplicationGUIGraphicalApplicationRectangle+draw()+area(): double
SRP違反の改善 GeometryApplicationGUIGraphicalApplicationRectangle+draw()+area(): doubleGeometryApplicationGUIGraphicalApplicationRectangle+draw()GeometricRectangle+area(): double
単一責任の原則の「責任」とはなにか? - 「責任 = 役割 = 変更理由」と定義している. - クラスの変更理由は1であるべき <=> クラスの変更理由が2つ以上ある場合そのクラスには2つ以上の役割がある.
単一責任の原則の適用を見極める - 役割が2つ以上あるときに分離するのが基本. - しかし,異なる役割ながら,必ず同時に変更が生じる役割は分離する必要なない. <=> 複数の役割が結合する理由を持っている事がある. - 過剰な適用は設計を不必要に複雑にする. - これは他の原則でも不必要な適用は良くない. - 「変更の理由が変更の理由たるのは,"実際に"変更の理由が生じる場合だけ」
第9章 オープンクローズドの 原則
オープンクローズドの原則 (OCP : Open-Closed Principle) - 拡張に対して開かれている(Open) モジュールの振る舞いを拡張できる. 追加の仕様要求がきてもモジュールに新たな振る舞いを 追加することでその変更に対処できる. - 修正に対して閉じている(Closed) モジュールの振る舞いを修正しても,そのモジュールの ソースコードやバイナリは影響をうけない. これはなんか矛盾している概念に見えるがなんとかなる.
client-serverの例 - Client,Serverともに具体的な実装を持っている. - Serverの実装が変更されるとClientも変更せざるを えない.(OCP違反) Client Server
解決策1 : 抽象を利用することでOCPを実現(Strategypattern) - 依存部分をinterfaceとして切り出す. - server abstractにしない理由→抽象クラスはそれを実装する側より使う側のほうが関係が密接だから. - Serverの実装が変わってもClientは影響を受けない. Client<>Client InterfaceServer
解決策1 : 抽象を利用することでOCPを実現(Strategypattern) - 依存部分をinterfaceとして切り出す. - server abstractにしない理由→抽象クラスはそれを実装する側より使う側のほうが関係が密接だから. - Serverの実装が変わってもClientは影響を受けない. Client<>Client InterfaceServer Piyo
解決策2 : 抽象を利用することでOCPを実現(TemplateMethod Pattern) - Policyクラス(方針クラス)は具体的な実装を持っている(一つ前のClientに対応). と同時に,抽象メソッドを持っている.(Client interfaceに対応) - Policyクラスの抽象メソッドを実装する実装クラスが ある(Serverに対応) Policy+ PolicyFunction()- ServiceFunction()Implementation- ServiceFunction()
OCPの実現 - Strategy Pattern , Template Method Patternが 典型的. - 汎用的な機能と,その機能の具体的な実装を明確に 分離する役割を持つ. - 使い所 : 最も変更されるプログラム部分にだけ的を 絞って抽象化を適用するように務める (早まった抽象をしないことも抽象を使うのと同等に 重要なこと)
参考資料 - アジャイルソフトウェア開発の奥義 - ロバート・C・マーチン - pp. 103 - 141