川村渇真の「知性の泉」

システム設計に必要な能力は幅広い


良いシステムの条件を最初に整理する

 ソフトウェア技術者なら、システム設計という言葉を必ず使うだろう。では、その具体的な中身は、みんなで同じだろうか。個人的には、技術者の視野の広さによって、かなり違うのではないかという印象を持っている。そこで、システム設計で検討すべき範囲を示す意味で、システム設計に必要な能力を整理してみた。
 システム設計に必要な能力を検討するには、システム設計の目的を適切に理解しなければならない。その目的を簡単に表現するなら「良いシステムを設計すること」といえる。「良い」という表現は様々に解釈できるため、もう少し深く定義してみよう。主な項目は以下のとおりだ。

良いシステムに必要な条件(非常にラフな)
・システムの内部に関わる点
  ・システム全体でバグが少ない
  ・厳しい状況下でも安定して動作する
  ・変更が容易で、変更後の信頼性を高く保ちやすい
・システムの価値に関わる点
  ・問題領域での役に立つ度合いが大きい
  ・利用者にとって、使いやすく運用しやすい
  ・問題領域での変化に対応でき、より長く使える

 システムの内部に関わる点は、ソフトウェア側から見た評価である。価値に関わる点は、問題領域側から見た評価といえる。この両面で質を高めなければ、良いシステムにはならない。
 この両面は、独立しているわけでなく、お互いに影響を及ぼす。もっとも多いのは、システムが持つべき機能の設計を間違ったため、途中で大幅な変更が発生し、多くのバグを発生させる状況だ。この場合は、問題領域側から見た失敗が、ソフトウェア側の問題を引き起こしている。
 長期的な視野で見ると、関係が逆になる。ソフトウェアの構造が悪いために変更が困難で、期待される機能を実現できずに陳腐化し、問題領域側での価値が低下してしまう。このように、両面とも向上させないと良いシステムには仕上がらない。

システム設計に必要な能力を整理すると

 良いシステムの条件を整理できたので、システム設計に必要な能力を洗い出してみよう。分析から運用までが対象となり、代表的な作業で求められる能力を挙げたみた。それが次の一覧である。なお、純粋に設計と呼べる範囲に限定するため、ソフトウェアや問題領域に関する専門知識は除いた。

システム設計に必要な能力
(分析まで含んで主なもの:ただし専門知識は除く)
・分析に関すること
  ・問題領域を分析する
  ・問題解決の実現性や効果を正しく評価する
  ・解決方法を仕様として規定する
・実現方法に関すること(システム全体)
  ・問題領域まで含めて適切な構造で設計する
  ・利用者側とソフトウェア側の役割を適切に切り分ける
  ・システムの設計内容を仕様として記述する
・実現方法に関すること(問題領域側)
  ・システム利用者(人間など)の役割を設計する
  ・人間のミスに対して、発見方法や対処方法を設計する
  ・問題領域側での重要度を考慮して、情報の見せ方を設計する
  ・利用者の活動目的に適した形で、システムの各機能を設計する
  ・将来の変化に対し、運用で逃げられる余地を多く残して設計する
・実現方法に関すること(ソフトウェア側)
  ・将来をある程度見通して、使用する技術を選ぶ
  ・システム全体の内部構造を適切に設計する
  ・エラー対処を上手に行い、信頼性を高める
  ・後からの変更に強い柔軟性を高める
  ・必要な箇所を見極めながら性能を高める
  ・他のシステムでも再利用可能な形で設計する
  ・問題領域側での意味が理解しやすい形で設計する
・開発作業に関すること
  ・設計内容や製作物を適切にレビューする
  ・ある程度の品質を確保できるレベルでテストする
  ・より良い標準化を提案し、積極的に守る
・使いやすさに関すること
  ・利用者が操作しやすく設計する
  ・利用者が使いやすい形で情報を見せるように設計する
  ・間違いや失敗を防止したり、影響を小さくする形で設計する
  ・システム全体を運用しやすく設計する
・設計という行為そのものに関すること
  ・何となく決めるのではなく、決定理由を理解して判断する
  ・決定の理由や過程を、他人に説明したり書類に記述できる

 見て分かるように、どれもがシステム設計で必要な視点である。それを能力として扱うのは、視点だけ持っているだけではダメで、その視点を実現できる力がないと意味がないからだ。能力と言うからには、その視点を実際のシステムで実現するための方法が身に付いていることを意味する。つまり、視点を実現するために、何を調べ、どのように整理および評価し、どんな点をどのように規定すればよいのかを理解し、実現可能な形で設計できなければならない。
 この一覧は、別な面も持っている。(全部の項目には当てはまらないが)良いシステムの条件を、より細かく説明した内容になっている点だ。これを見れば、良いシステムとは何かを、前述の簡単な条件よりも具体的に理解できるだろう。

システムの評価に欠けている視点

 世の中では、成功または失敗したシステムを評価することがある。そのとき、どんな点を見ているのだろうか。残念ながら、ほとんどのケースでバグの量しか見ていないようだ。運用し始めてから発見されたバグの数が、システムの規模と比べて多いか少ないかで評価する。
 この業界には、新しい開発方法論がときどき登場する。最近話題に上っているのは、CMM(Capability Maturity Model)とXP(Extreme Programming)だ。こうした方法論を評価するときも、同じようにバグの量で優劣を決めている。新しい評価の多くは米国で行われているので、米国でもそんな状況なのだろう。
 開発方法論の評価は、バグの量による評価だけで良いのだろうか。ダメだとしたら、どんな視点で評価すべきなのだろうか。この疑問には、前述の「良いシステムの条件」が役立つ。見て分かるように、バグの量は、6項目のうちの1つでしかない。他の5項目を調べて評価しているのは、どれぐらいあるのだろうか。とくに、問題領域側での価値を調べて評価している例は、ほとんど見たことがない。
 6項目の位置付けを考えたとき、バグの量が一番低い項目になる。バグの少ないことが、運用できるシステムの最低条件になるからだ。バグの量が一番低いレベルなので、バグが少ないと判明したら、次のレベルとして別の項目を調べなければならない。問題領域での役立つ度合い、使いやすさや運用しやすさなどだ。こうした点まで比べないと、本当の優劣は付けられない。そうしないと、バグが少なければ、全部が良い開発方法論になってしまう。そんなはずはないし、こんなやり方では評価方法のレベルが低すぎる。
 残りの5項目の評価では、「システム設計に必要な能力」で挙げた内容が役立つ。これらの項目をより詳しく掘り下げると、評価方法が導き出せる。当たり前だが、こうした評価方法を作るためには、その項目の設計能力を身に付けている必要がある。おそらく、評価する人がその能力を“持っていない”から、評価項目として取り上げられないのだろう。
 バグの量ばかりに注目するのは、6つの中でもっとも調べやすい項目という面も見逃せない。しかし、それ以上に悪いのは「良いシステムとは何か」を規定せずに、システムの評価を行っているという手順そのものだ。システムを評価する前に、採用している評価方法自体を評価すべきである。そうすれば、バグ以外の点でも評価すべきだと気付くはず(バグがなければ良いシステムだなんて、普通なら思わないはずだから)。
 こうした現状なので、バグが少なければ良い方法だという意見が世の中に出回っている。そして、そんな評価方法に何の疑問を持たないソフトウェア技術者が“世界中に”多い。本当に困った状況だ。

システム設計能力とプログラミング能力との関係

 システム設計という言葉の話題に戻ろう。ここまでで、良いシステムの条件を規定し、その実現に必要な能力も洗い出した。能力の一覧を見ると、システム設計に含まれる内容も見えてくる。ソフトウェア側の設計だけでなく、問題領域まで含めた設計を含んでいる。さらには、解決方法の評価、使い勝手や運用しやすさ、レビューやテストといった開発用の技術もある。この作業をすべて含んだものがシステム設計の中身だ。
 ところが、ソフトウェア側だけの設計(主にソフトウェア構造の設計)をシステム設計と考えている人が、かなり多いように思われる。そんな考え方は、システム設計に関する話題の発言として確認することができる。共通しているのは、システム設計と言いながら、良いシステムよりも良いプログラミングを目指している点だ。あくまで中心は、プログラムなのである。良いシステムには良いプログラミングが必要だが、それだけでは良いシステムを構築できない。
 システム設計能力とプログラミング能力との関連も知っておきたい。前述のようにシステム設計能力は幅広いので、毛色の異なる複数の能力が求められる。ソフトウェア側の設計能力は、プログラミング能力に共通する部分が多い。そのため、プログラミング能力が高ければ、比較的容易に能力を身に付けられる。
 しかし、問題領域側の設計能力に加え、ソフトウェアまで含んだシステム全体の設計能力は、プログラミング能力と性質がかなり異なる。こちらは、汎用的な問題の解決能力に近く、プログラミングのように属性が明確に分かっている状態ではない。混沌としているように見える中から、属性自体を探し出したり、本当の問題は何かを見極めたり、利用者の特性を調べたりする。その上で、最適と思われる解を設計して規定なければならない。
 もう1つ、使い勝手や運用しやすく設計する能力も、プログラミング能力とは性質が異なる。こちらのほうは、使いやすいインターフェースや、運用でのトラブル防止方法などを勉強しないと、良い形に設計できない。また、情報を分かりやすく整理して見せる方法も、習得する必要がある。表示画面だとデザインの美しさに注目しがちだが、使いやすさや情報整理の方が重要だ。
 さらに、設計という行為自体の基本を理解することも大切。設計とは、何となく決めるのではなく、他人に説明できるほとの明確な理由を持って決定する行為である。判断が難しい場合でも、簡単には判断できなかった理由と、推測した前提条件などの判断材料を示さなければならない。こうした行為を続けることによって、設計の基本能力もだんだんと伸びる。
 ここまでの説明で、システム設計能力には、プログラミング以外の要素がいくつも含まれる点が理解できただろう。それだけに習得は難しいし、プログラミング能力だけを高めていては、いつまで経っても身に付かない。10年というような長い期間をかけ、計画的に身に付けていく必要がある。
 よく見かける勘違いは「プログラミング能力が高ければ、システム設計能力も高いはず」という考え方だ。日本だと、米国の有名プログラマーのシステム設計能力が高いと信じている人が多い。しかし、ここで説明したような点を知れば、そうでない可能性が高いと分かるはずだ。開発方法論の優劣をバグの少なさで判断する人は、システム設計をよく理解していないと推測できる。

開発方法論の評価は、良いシステム設計の条件を基礎に

 世の中には、新しいシステム開発方法論がときどき登場する。その評価も、良いシステム設計に何が求められるのか理解して行わなければならない。バグの少なさだけで評価するのは、止めるべきだ。
 どんな開発方法論でも、前述のようなシステム設計のすべての面をカバーしているわけではない。そのため、どの部分をカバーしているのか、まず最初に洗い出して整理する。これが明確になると、その開発方法論の位置付けも分かってくる。
 開発方法論を利用するのは、良いシステムを構築するためなので、カバーしていない部分を何かの方法で補わなければならない。その際には、具体的に使える方法のうち、一番適しているものを選ぶ。選択した方法が、開発方法論の方法と矛盾したり相性が悪くないか、調べる必要もある。もし矛盾や悪い相性が見付かったら、別な方法に切り替える。
 こうして組み合わせた状態こそ、その開発方法論の現実の姿になる。それを実施してみて、現実の効果を評価する。評価では、バグの少なさだけでなく、問題領域での役立つ度合い、使い勝手や運用しやすさなども含めて、総合的に判断する。
 以上のような方法で評価するのは、良いシステムの構築が目的だからだ。出来上がったプログラムだけを見て、判断してはならない。あまりにもありがちなので、とくに注意する必要がある。
 物事を評価する場合、基礎となるのが論理的な思考や検討だ。しかし、論理的に考えたり評価する訓練を受けてない人がほとんどなので、とんでもない考え方がまかり通っている。たとえば、自分と対立する相手への「〜の呪縛を受けている」とか「〜が潜在意識に埋め込まれている」という意見だ。これらは論理的な内容ではなく、相手の印象を悪くするだけでしかない。こんな意見など言わないで、もっと具体的に、どの部分がどのように悪いのか、明確に指摘すべきである。そうしないと、マトモな反論ができず、議論として成立しない。当然、良い評価にはほど遠い。
 こうした論理的でない意見は、どんな分野でも数多く見受けられる。適切な評価を行うためには、論理的な思考方法の習得が先に必要だ。プログラミングが得意なら論理的な思考も得意だと思っているかも知れないが、実際にはまったく別物である。論理的な思考は、一般的な問題解決に近く、プログラミングとは性質が異なる。そのため、プログラミング能力と論理的な思考能力に強い相関関係はない。
 悪いタイプの技術者に共通するのは、外国の有名な技術者が主張する内容を“盲目的に信じる”点だ。何でも都合良く解釈して、良いことばかりを強調したがる。本来なら、まず疑ってかかり、論理的な思考を基礎に評価すべきである。良いシステムの構築には、どんな要素が必要なのかという視点を持ちながら。盲目的に信じるのは、論理的な思考能力の低くさが原因なので、真っ先に勉強しなければならない。

プログラミング以外の設計ノウハウの流通が不可欠

 システム設計に必要な能力を習得しようと考えたとき、何が問題になるのだろうか。一般の技術者にとっては、勉強しようと思っても、教材や資料が手に入らない点が一番の問題。プログラミング以外の設計ノウハウは、ほとんど流通していないからである。本コーナーでは設計ノウハウの一部を公開しているが、このようなサイトの数は非常に少ない。
 理想的には、雑誌や単行本を通じて、何種類もの設計ノウハウが入手できればよい。しかし、その可能性は極めて低そうだ。まず、買い手側に問題がある。多くの技術者がプログラミングに関係することしか興味がないため、単行本を出しても売れない。そんな状況を知って、出版者側では躊躇するか、非常に基礎的な内容への変更を求める。基礎的な内容に変わると、本当のノウハウを盛り込みにくい。もしレベルの高いノウハウ本を出すとしても、部数が期待できないので高い価格を付けるしかなく、それも売れない原因になるため、中止を決めることがほとんどだ。結果として、本当の設計ノウハウが流通しない。
 この状況は、おそらく当分変わらないだろう。設計ノウハウを求める人が増えるには、ソフトウェア技術者の平均レベルが向上するのを待つしかない。それがいつになるか分からないので、習得したくても勉強する方法が得られない状態が続くと予想する。本コーナーでは、非常にゆっくりとしたペースになってしまうが、設計ノウハウを少しずつ公開しようと思う(他の研究テーマもあるため、ペースは相当に遅くなるだろうから、あまり期待しないでほしい)。
 1つだけ、できることがある。自分で考えることだ。同じ意識を持つ仲間と一緒でも構わない。前述の「システム設計に必要な能力」の各項目がヒントになるので、それをもとにしながら、具体的に何をしたらよいのか真剣に考えてみよう。実際のシステムを例に考えれば、設計に必要な要素が少しずつ見えてくるだろう。

(2001年2月23日)


下の飾り