2016年5月4日水曜日

ソフトウェア設計の最適化方法

ソフトウェア設計の最適化方法


ソースコードとは
 まず、ソースコードで求められているものはなんだろう。というテーマから入って説明したいと思います。
 世の中には
 ・ウォーターフロー開発モデル
 ・アジャイル開発モデル
 ・アスペクト開発モデル
 ・プロトタイプ開発モデル

などいろんな手法が考案されて、様々な現場で利用されているのではないでしょうか。

運用する時は、組織体系に合わせて世の中一般の開発モデルをカスタマイズされているので
A社、B社が同じ開発モデルを利用していて、あるプロジェクトで情報を共有して共同開発しようなんて場面に出くわした時は
必ずといって情報の一元化を行いましょう、という合言葉とともに本来不要なプロセスが発生する。
(同じ開発モデルだから相性はいいが、完全一致させることは不可能と思われる)


情報とは
 熱力学のエントロピーという言葉を耳にしたことがあると思う。

これは、
 集約されている状態は秩序が保たれていてエントロピーは小さく、
 散っていて無秩序な状態のことをエントロピーが大きいと表現している。

この考え方は情報分野にも当てはめることができる。
圧縮アルゴリズムを勉強した人はハフマン符号化を学ぶときに情報エントロピーという言葉が出てくる。
情報エントロピーとは、これ以上圧縮できないデータ量の事で、冗長性が非常に小さい状態のことを意味する。

前の話で組織間で出てきた「情報の一元化」とは、
お互い同じ情報を扱っているのに散ってしまう情報を打破するために行われる手法だという事を意味している事が分かる。
もう少しわかりやすい表現に変化させてみよう。
「情報の一元化」を別の言い方で表すと、「枠組みの中で情報の整理整頓を行う」となる。
ここで出てきた枠組みの中でというのが社間を意味し、そこで得られた情報を整理整頓を行うことである。
つまり社間では情報の中身ではなく、情報の出入りの話であって、これは仕様書などのドキュメントを台帳管理しようという事を示している。


ソフトウェア仕様とエントロピー
 少しずつ現場レベルに考え方をシフトしていく。
ハフマン符号化に出てくる情報エントロピーの考え方でいくと、
「冗長性をなくす」事でエントロピーが小さく、秩序が保たれているとこである事を意味している。
この考えは同じものが無ければまとまっているように思えるが、ソフトウェアの場合は時間軸があり仕様変更があるので、情報エントロピーという考えで情報をまとめることは難しい。
そこで原点に戻って、熱力学のエントロピーには「エントロピーの増大の法則」というものがあり、時間が経過していくとエントロピーは増加するというものである。

この考えを当てはめると、ソフトウェアは時間と共に仕様変更が行われ、エントロピーが増大していく。

と言える。

つまりソフトウェアの性質上、仕様変更が発生して、追加・変更・削除が設計・コードに反映される。

ソフトウェアの変化を管理する事でエントロピーの増大を記録することができる。(減少はしない)

裏返しにするとエントロピーが減るような仕様書は無い、仕様変更は工数が発生して費用が発生するという事が言える。


ソフトウェア設計とエントロピー
 仕様変化することでエントロピーが増大するという事を説明した。
次に仕様と設計について述べていこうと思う。

熱力学でいうと 熱エネルギーは 高いものから低いものへ移動していくというものがある。

これを仕様=熱いもの  設計=低いもの に例えると、
仕様書から設計書へ情報を移すと散らばる(千差万別)と表現してみると分かりやすいのではないだろうか。

設計書を書くとエントロピーが増大していくのは自ら苦しめていくようなものなので、
よくある事例を出すと書き方の統一である。

最近ではUMLで図の書き方を統一しようという動きはあるが、
設計書に適用する場合は運用ルールを決めて、書き方のテンプレートとガイドラインを用意しておくと良い。
また仕様変更で変化した場合は新たにドキュメントを作成しバージョン管理して
変化内容と以前の仕様、最終仕様を明確化しておく事とトレーサビリティが保たれる。


ソースコードとエントロピー

現場でよくあることは、
・Aさんのコードはまとまっていて見やすいコードを書く
・Bさんのコードは乱雑なコードを書く

というように人によって書き方が変わって秩序が乱れエントロピー増大に繋がっていることがある。

これも設計と同じように、書き方のテンプレートやガイドライン、フレームワークを利用する事で
書き方が統一できるようになる。
もう少し細かく書くと、
仕様とは、構造と機能の2つに分類され、
構造はフレームワーク
機能はユースケース、ステートマシン、外部通信仕様などに分類して表せることができて、それぞれに追加・変更・削除
がある。

機能の追加や変更、削除はオブザーバブルなものであって、
ある機能を 
 使う(Main)
 動かす(Sub)
 評価(Test)

に分けることで分担作業が可能になって機能を分割しやすくなる。

より具体的に説明すると、
 Mainクラス(上位:使う側)
 Subクラス(下位:実働側)
 Test(Mainクラスで使い方サンプル集みたいなもの)

の3つに分けて実装し、
機能の管理はMainで行われて、機能の実装はSubクラスで行う
TestクラスでSubクラスの品質評価を行い、
Mainクラス側でビジネスフローを実装する。

こんな具合になる。
これでエントロピーが減らせるのか?と思うだろうが、
仕様変更が起こると 仕様変更(Main)、機能変更(Sub)、変更に伴う評価(Test)
それぞれに作用が行われ、どの規模の変更が起きたのかが現場レベルで実感しやすくなり、
対費用効果の算出などに有用であることが分かる。
例えば、
 ・仕様追加ならMain・Sub・Testに影響
 ・仕様変更ならMainに影響(ビジネスフローは人力で評価を想定)
 ・機能変更ならSub・Testに影響


ざっくりまとめると、
 ・仕様書のバージョン管理
 ・WBSによる機能対応表
 ・ソースコードの実装を分担化

となる。

より精度の高い最適化を行うのであれば、エントロピーの増大について学んで
エントロピーを減らすことはできない事を理解して、いかにして増大するを抑止するかを考えてみると良いと思います。

Androider