4.設計をしてみる
ここまではプログラムの動きについて書いてきましたが、実際にプログラムを作る際には最初から直接プログラムを書くというのは稀かと思います。
勿論個々人の経験や能力に違いはありますし、目的も違う以上最初から手を動かして作り始めるということもできます。
しかしここではそうではなく一旦プログラムの全景を考えるというフェーズを経たいと思います。
本来は要件定義として利用者・作成者での合意フェーズもありますがその話は一旦おきます。個人ベースではどのように動くのかという視点で考えます。
一番最初に書いてみたように、プログラムには出力と入力が存在します。
特にプログラムで何かしたい、しなくてはならないという時には目的の方が大事で、要は出力を求めているというところから出発すると思います。
そして次に利用できるデータはどのようなものかという思考過程を経ます。
その二点が決まれば間をつなぐ各種の処理をどのように作り上げるかを考え始めます。
ただここで気を付けて欲しいのは出力の要望・要請があっても入力データによっては必ずしも出力が得られるわけではないということです。
いくつか例によって考えましょう。
料理ではかつ丼が欲しいと言っても材料に豚肉や卵が無ければ作ることは出来ません。
他に、日本のある年代での指標を年代と追跡比較したいと思っても手元にあるのがアメリカのデータだけであればこの出力は得られません。
こういった場合そもそも出力が得られないことを納得し、ゴールの修正が必要です。また、もしデータを何らかの手段で得られるのであれば特段の修正は不要です。
問題は出力の為に適したデータが存在するか否かです。これは単純な話ではありますが入手可能なデータが非常に限られている場合にどうしても出力もある程度予想した範囲を越えないということも起こり得ます。
そういった場合輝かしい結果と言うのは得ずらいものですが、そこで何か特殊な操作をすることにより目覚ましい成果となったりということも無いわけではありません。
ただ気を付けていただきたいのはその操作というものが本当に許されるものなのかという点です。
この後に書くことではありますが、数値計算にはどうしても理論やプログラム内部の処理だけでは決めきれない数値と言うものが存在します。
このように人間の意思や選択が入り込む余地がある以上その正当性は一歩ずつ確かめるほかありません。自然科学分野であれば実験で確かめるという手段も取るというのも一つの検証として有効ですが、必ずしもその手法がとれる分野ばかりではなく計算結果と手法全体を業界の基準や社の基準、監督官庁や団体から公表された指針などに従って合致を確認することが多いのが実情です。
あまり実感がわきづらいかもしれませんがこの点は業界によっては非常に重篤な瑕疵に繋がることもあるため、正直今作のどの点よりもご記憶いただきたい部分です。
今作では料理に例えて紹介をしてきましたがこちらは場合によっては食品偽装と呼ばれるレベルと言っても過言ではないかもしれません。本来の要求に対して意図はともかくそれと違ったものを出すというかなり危険な行為で、もし美味しければ良いという次元の話ではありません。
もし使った食材の中にアレルギーがあったらどうでしょうか。注文者はその危険を知って避けたのに偽装行為の為にその回避行動が無に帰したばかりかさらなる危険が襲ってきたという事態になってしまいます。
これは互いの信頼行為を破壊するばかりだけではなく飲食店の経営(プログラムの作成者やその使用者に対する信頼)も毀損しかねません。
また研究の世界では時折不正の事例として報道などがありますが、そういった不正に近しいこともこの問題では起こりえます。
さて少々重い話に寄り道してしまいましたが、肝心の間の処理に関して考えます。
一番シンプルなのは最初の例の様に入力をそのまま出力することで、中間処理は何もありません。少し手を加えると入力が数値であれば足し算引き算を行ったり、入力が文字ならその文字をくっつけたりというものが考えられます。これらをさらに複雑にしていきましょう。
するとそれは様々な計算ルールを決めていくということに他なりません。
入力の値によって場合分けしたり、ある方程式に従って四則演算を行ったり、四捨五入の処理を行ったり、そして何よりその処理をどのような順番で組み合わせるか。
この順番と全体の流れは計算フローとも呼ばれ、複雑な処理では分岐や繰り返しを多数含むためそれ専用の書類を用意して把握するということも珍しくはありません。
ここが先に最初から書き始められる人もいるといった大きな点であり、頭の中で計算の全体の形を思い浮かべられればそのままプログラムを書き起こすことが出来ますが、慣れない場合には一度簡単にフローを書いてからプログラムを書くという方針があり得ます。
書きながら考えることも可能ですが全体の流れを把握してからプログラムを書くことで目的や使うべき式がどのような位置で使用されているかも捉えられるため利点が多いかと考えます。
ここで使う式について考えてみると、最近のプログラム業界、特にpythonに関しては公式や外部のライブラリの充実が素晴らしいものと言えます。
簡単にこのライブラリとpythonについて紹介しておきますと、pythonと言うのがプログラムの言語の一つで書きやすく読みやすい言語となっています。その守備範囲、プログラムで処理できる領域もかなり広く数理的な数値計算以外でもweb系機械学習等々の実装が可能です。ライブラリは色々処理をする際に、処理のコードを色々な団体や個人が公開しておりそれらをダウンロードすることで利用し1からコードを書くのではなくある程度簡単に処理が実装できるようなものとなっています。
ここでpythonを紹介したのはとりあえず知名度的にわかりやすいものだったためで他の言語でライブラリの公開がそこそこの量あるものであれば何でも読み替えていただいて問題ありません。
話を戻すと使うべき式を考えた時に複雑になれば成程あまり自分で一から書くということは少なくなるという傾向があるということです。
これはプログラムをただ実装するという点では大変喜ばしいことなのですが設計側で特にその計算結果の精度を気にする側の人間であればその中身は知っておくべきかと思います。
まずプログラムそのものに立ち入る前に設計を紙面に起こすようなものであれば理論的にどんな式を使うかというのは明示されます。それは最初からわかっている場合もそうですし、自分でもっと基礎的概念から問題に合わせて手計算を行い導出するものかもしれません。
いづれにしても実装対象となる式というものが分かるということが重要です。
設計段階においてはこの式が間違っていた場合書き起こしたプログラムは該当部分を全て修正することになります。
またその結果を用いて何か処理をする、という処理の場合にはその処理と結果にも影響が波及します。
最終的な出力が影響を受けることは当然ですが修正範囲がどこまでに及ぶかは書き方次第な面もあるためこの点ではできる限りミスなく、出来れば修正が軽微なもので落ち着くような設計だと後が楽です。
このあたりも書籍が1つかけるような話が色々と転がっているものですが何となくそういうものと理解いただければそれでいいかと思います。
そしてこの理論式が導出されればいったん理論的にその式を味わいます。切り口として一旦プログラムで書くということを忘れて、数学的に解くことは出来ないか、極端な値を代入したときの振る舞いはどうか、式の中に項が複数ある場合1つが飛びぬけて大きな値を持っていて他の項はほぼほぼ意味がないような値の場合には1つ以外の項を消すことで近似的に式を解けないか、というものがあります。
特に数学的に解けてしまう場合は非常に嬉しくコンピュータの問題から生じるもの含めてプログラムによる問題はほぼ全て解決されてしまう為最高の結果とも言えます。
とはいえそれはほぼあり得ない程の確率であり実質的には他の観点でのチェックとなります。
この点は意味があるのかという疑問もあるかもしれませんが、プログラムの実装前にその式の傾向を知ることで、そもそも式が間違っていることや式は合っているものの実装で間違っているということに気づきやすいという利点が上げられます。
特に統計的分析も行う場合にはある項の寄与が圧倒的に大きければ分析の方向性も定めやすいという嬉しさがあります。
さらにもう少し踏み込むと、プログラムで実装することは可能だが理論的に曖昧さがある、あるいは理論的には間違っているというフローも存在したりします。
これは特に複数人での開発を行う際の観点にはなりますが、プログラムの前に理論的な記述を確認することで致命的なミスの回避を行うという事例です。
特に分析の内容や処理が複雑な場合には正負の符号の入れ替わりや計算すべき関数のミスと言った間違い、そもそもの計算を可能とするための前提条件など考えるべき要素が増えるため、実装後のプログラムではなくそのための紙面上での評価が大きな意味を持ちます。
中でも計算の前提の間違いは傷が大きくなりやすく、発覚したのが計画の後の段階だったりすると開発期間的にも心情的にも相当のダメージとなります。
料理で言えば作るべきものがフレンチのフルコースと思っていたら中華の満漢全席だったというぐらいに大きな違いになってしまいます。
このようにして理論的に式を楽しんだり、じっくりと見つめ直した後に実際にフローに従いプログラムを書き起こす段階に入ります。
この段階に入ると書きやすいやり方、プログラムを書くためのエディタは何を使うのか、改行のやり方などなど様々な派閥や流派が存在していますし、何より実践書が数多く出版されています。
実際に手を動かす方法や勉強法はそういった書籍から学んでいただくとして、コードを書くという点では一点に絞って語りたいと思います。
先程も書いたようにプログラム中には外部にライブラリとして計算コードが一式揃っているものが相当あります。
そういったものを利用すればライブラリ利用者は自分の使いたい入力のデータに対して少し調整は行うにしてもほぼそのままそのライブラリのコードを用いれば計算処理は済ませることができます。
ここに懸念点があり利用者はライブラリの中身をどこまで知るべき・考えるべきかという問題があります。
特に計算処理として何らかオプションを指定できる場合にはそのオプションを選択しないデフォルト状態がどのような計算過程を経るのかも知らなくてはならないのか、という指摘もありえます。
ここについて、私の意見としては全体の計算の中でそのライブラリを使用した部分がどこまで重要度を持つかという点で評価すべきと考えます。
あまり直接的にこうすべきと断言できずに読者の方々には大変申し訳なく思うのも事実なのですが、できる限り一般的なプログラム全般に対して言及する以上はこのような書き方になってしまうことをご容赦願いたく。
というのも、プログラムにおける計算処理は重要度が高い部分、そうでもない部分とには別けることが出来ます。これはミスがあった場合に出てくる結果がどれほど信頼できるかという観点で評価できます。
出力の数値そのものが大事であれば、ミスがあっても表示のレイアウトが変わる程度で数値そのものに影響がないなら重要度は低く、ミスがあった場合数値が変わったり全く別物となるような部分であれば重要度は高いと判別します。
さらにこの重要度の高い部分でも相対的に上下関係は存在しうるものではありますが一旦はこのような重要度での評価で落ち着けます。
こうして重要度の高いと評価をした部分にライブラリによる計算が存在するとしてみましょう。
ライブラリの計算方法を弄った場合には影響が出力に及んでしまう以上そこはその仕様を知らなくてはなりません。
幸いなことに大概のライブラリにおいてはどのような仕様になっているかを公開しているためその公開情報に基づいて探求すれば問題なく知識を得ることはできます。
問題となるのはこういったライブラリの計算仕様が存在しない場合やライブラリの使用に数学的に前提が存在する場合です。
前者から考えましょう。仕様情報を公開していないということは上記の処理フローに近いものはなく、プログラムとして記述されたコードをそのまま読解することを要求されます。
数値的に弄ってみてその結果からある程度の傾向を予測することも可能でしょうが、それはテストとして用意したパターンに対してどれだけの傾向があるという以上のことはわからないため非常に極端な状況設定や複数の面倒な組み合わせの場合にはどのような挙動となるかわからない以上全てを網羅できる、コードそのものを確認するという工程は避けられません。
特に常にプログラムの処理が動き続けることに重きを置くような環境ではそういった複雑な場合において処理がエラーを起こしてしまうというのはかなり深刻な問題となりえます。
そのような状況を先に避けられるだけの情報は探っておくべきですし、もしその情報が見つけられないかコードそのものが読めない場合には代替案を検討すべきと思います。
もう一方の数学的前提の問題も考えてみましょう。これは厄介なことにそのライブラリそのものがそのプログラム、コードを実行するときに入力データに何かしらの要求をしてくる場合とそれが全くない場合とが存在します。
コード実行時にそういった要求・要請がはっきりとわかり、もし満たさない場合にエラーメッセージなどを出してくれればいいのですがそこは必ずしもそうとは言い切れません。
いくつかの計算方法をオプションとして用意しておいて数学的前提を満たさないか満たすかどうかで手法を変えて別個に実行するコードの内容を変えているという運用が一般的と思われます。
ライブラリの作成者からすればこのようにしておけば余計な判別とエラーメッセージの出力という処理は避けられますし仕様を読んでおいての一言で済みます。
反面利用者からすれば自分の使っているデータやそのライブラリの手前までの計算での処理が前提を満たしているかどうかを確認するという工程が一つ挟まれることになります。
これ自体は少々面倒とも思うかもしれません。しかしそもそも外部ライブラリというメリットを享受しようとしている以上その点は受け入れるべきかと思いますし、数学的前提についてじっくりと理解した上で自分の使用するデータや計算と噛み合うのかを検証しなくてはならないものと考えます。
先にも触れたように数値計算ではある程度の任意性が含まれるというようにこの辺りの計算手法の選択も当人の理解のレベルや目的によって変化する部分があります。
ここについては、特にその結果を他人にも伝える場合には胸を張って最適な手法を選んでいると説明できるくらいには内容を認識し理解しておくことは避けられないと考えます。
もし自分ではなく社やチームのコードで、このようなライブラリの利用における前提への違反か近しいものがあると感じた場合には作成者やチームのメンバーには確認すべきですしその結果が重大なものであるほどに昨今のコンプライアンス事情からも重要性は高いと考えるべきと思います。
少し長い章となってしまいましたが設計はプログラムの実装のただの前段階と言うものではなくかなり深遠で時によってはもう一度プログラムを見直すという観点にも影響があるものとご認識いただけたかと思います。
少々実装寄りの点も含めてしまいましたが業界によっては知らずに実装を続けると他者が不安を覚えるような内容になったりするというのは普通に起こりえる事例ですので今後そういった事例が世の中から少なくなればと思っています。




