「天才プログラマーが作った糞コード」という都市伝説
- 「一人の天才プログラマーがほとんど一人でシステムを作ったがドキュメントはなくて誰もメンテできないときってどうするの?って話」 https://togetter.com/li/1549364
1人の天才プログラマーがシステムをほとんど1人で作ったんだが、ドキュメントが残っておらず、他に誰もメンテできる人がいない。
— やまぶん (@yamabunmath) June 25, 2020
みたいな状況って、みんなどう対応してるの?
保守不可能な糞コードは山ほど見てきたけど,そんな状況は一度も見たことがない.*1
ヘッポコ管理職が,社長を説得するためにそう説明しただけじゃないかね.まさか「自分はバカなので,デザインパターンとか平行プログラミングとか分かりません」なんて口が裂けても言わないもの.*2 またヘッポコプログラマーには自分に理解できないコードが,それが自分の理解を超えているからなのか,単純にダメなコードなのかの見分けがつかない.
糞コードは一目見るだけで吐き気がするけど優れたコードは芸術作品で,読むのに感動すら覚える.真の天才が作ったコードなら保守も楽だろう.*3
実際にそういう状況が起きたときは,天才のせいではなくて,
- 最初からヘボプログラマーが書いたヘボコードだった.
- 最初はキレイに書かれていたが,ヘッポコな奴らが理解できずに後から無秩序に書き足したり,コピペしていったので糞コードになった.
- コード自体はマトモだったけれど,それを間違った方法で他システムから呼び出したり,他へ組み込んだりした.*4
- コードの問題ではなく仕様の問題だった.仕様を保存しておけばいいものを,口頭で伝えるのみで議事録すら残っていなかった.或いは議事録と称するものはあったけれど,肝心の詳細については書かれていなかった.
- 仕様が現場に伝えられなかった.なぜそうなってるかは現場にも聞かされてないので,作った本人にも説明できない.
- 完成する前に納期が来た.会社が潰れた.開発者がクビになった.*5
などのパターンの方が多そうに見える.
言語がC言語やJAVAではなくアセンブラ、サーバは昭和50年頃のオフコン、データベースはVSAM、外部記憶媒体は8インチフロッピーディスクっていうパターンをリニューアルしました。もう1社のシステムはもはや手遅れ。数億出すからと泣きつかれたが。
— DJフォンタナ@ICT (@DJ_FONTANA_ICT1) June 26, 2020
こういうのもな…….もはやドキュメントの問題ではない.
最初からイマイチだった例.イマイチだったからその技術は完全に廃れて,今では誰も使ってない.
これもまれに良くある.*6
一人のポンコツプログラマーが作ったシステムがあって資料が残ってない
— 雪山雪太郎 (@yukiyama2003) June 26, 2020
なら割とよく見る
外注で常駐した所はそんなの私にやたら回って来てましたが、改修や障害対応は突貫で必要箇所だけ絞ってソース解析してましたね。私も抜けたら、システム更改まではまた後任が似たような事繰り返し。
— Matagi (@_Matagi_) June 27, 2020
その場しのぎの変更増強繰り返して奇形のようなシロモノと化した外部I/F、開発者の意図伝わってなくて現場ではトリッキーな使い方されている謎画面、ほぼ同じ内容の処理しているのに何十にも増殖してる不思議なバッチexeなど、そんなの真面目に改修していたら精神的ダメージ蓄積しましたけどね。
— Matagi (@_Matagi_) June 27, 2020
わかる.
これって「コード自体はマトモだったけれど,それを間違った方法で他システムから呼び出したり,他へ組み込んだりした.(さらにその間違った呼び出しコードをアチコチにコピペするとか.)」 のパターンかな.
1 ソースを読んで項目転送表を作る
— W.D. (@WD4096) June 26, 2020
2 パフォーマンスの悪い箇所から順次リファクタリングしていく
という対応が多いです。書き直したいけど書き直すコストが実益に対して高い場合とか、悔しいですが見送ることがあります。
ループのネストが1段目と2段目が逆であるべき箇所が2桁見つかった時とか。
全部手探りでソースコード直してたのはいい思い出です^^;
— NORI@転職アドバイザー (@susume_engineer) June 25, 2020
周りからは頑張れとしか言われませんでした。
その時、僕は新卒でした。
ドキュメントはドキュメントで必用だけど,それはここで議論しているような次元で必用なわけではない.解説資料は「あればいいな」だけど,天才プログラマが書いたコードにとって必用だとか,それがなければメンテできないというほどでもない.*7
数値計算とか非同期処理のように,ソースコードからその挙動を把握するのが困難な領域もある.だがこれはプログラムの性質的に把握しにくいだけであって,天才だからという話ではない.平凡なプログラマが作ったとしてもやはりメンテは大変.可読性も保守性も,天才プログラマが作った時より落ちる場合の方が多いだろう.*8
「組込なんかの省メモリなシステムで,天才がトリッキーなことをしているコードは読み難い」というのもどこかで見たけど,これも原因はメモリが少なすぎることであって,天才だからじゃない.天才が作った物よりボンクラが作ったものの方が,遙かに読み難かったり,メモリ消費が大きかったり,そもそも動かなかったりする.
クソコード動画「Managerクラス」#すえなみチャンス暑気払い pic.twitter.com/3FSQDkXfHu
— ミノ駆動 (@MinoDriven) August 3, 2019
ブクマカの反応: https://b.hatena.ne.jp/entry/s/togetter.com/li/1549364
ほんとにコレ.
糞コードというものは,変数名やメソッド名,クラスやメソッドの切り分け方,メソッド引数一つとっても,センスのなさが際立っていた.天才プログラマーの作ではありえない.
http://www.pro.or.jp/~fuji/mybooks/cdiag/
*9
これが可愛く見えるレベル.*10
- id:kotetsu306 一人の天才プログラマーが作ったコードを使用 → 技術力を評価した大手企業が会社を買収 → 天才は転職し、ドキュメントの無いコードだけでは技術力も発揮できない みたいなケースなら見た
会社を買収したけど,そのプログラマの待遇は変わらず最低のままだったとかいう,良くあるパターンなのかな.
- id:quick_past コメントもそうなんだけど、ほんとにすごい人って、自分でも誰でもメンテすることを考えて、すっきりしたコード書くよね。妙に凝ったコード書く事が技量であるかのように勘違いされてる。
- id:syuu256 天才が作ったならば、ドキュメント無しでも、ドメイン知識が有ればソース読めば解るはず、天才ならね
書いた本人だって1年後に保守するときは書いた内容なんて忘れてる.一流プログラマが読んで理解出来ないようなコードは,本人にとっても糞コードだから.
- id:taguch1 ああ、地図か。なんとなくわかった。あれ系のコードは天才というか意味わかんないコード多いよな。算数得意な人の分野だし普段Webアプリとか業務ロジックとか書いてる人にはしんどい領域。
たまにコレもある.その場合でも糞コードにはならないけど.
また書くにしても,せめてそのコードを理解できる程度のプログラマを付けないと,素人をつけても内容が理解できないので結局ドキュメントは作られない.管理職が「人を追加したのになんで書かないんだあ」とか喚いても無意味.
- id:raamen07 俺の世代だとGoFのデザパタとかS.O.L.I.D原則とかDDDとかMVC,MVP,MVVMとか流行ったけど、行き着いたのはシンプルに書くこと、な気がする。こっから先まだなんか流行るのかもしれないけど。
それ逆だと思うぞ,
「シンプルに書く」が原点.GoFなどの技術はシンプルに書くための道具だから,そういう技術を駆使した方がシンプルなコードになる.なってないのは単にプログラマのスキルが低いだけ.
しかも間違った入門書も多いんだ.憂鬱本みたいに.
ダメプログラマと一流プログラマの書くコードの違い
あくまで一例だけど.
- バグが残ってる.それも致命的なバグが沢山残ってる.
- 変数のスコープがやたら拾い.典型的にはグローバル変数だが,それ以外の変数についても無駄に広い.
- 型の使い方が間違っている.*11
- 適切なアルゴリズムを知らない.効率的なアルゴリズムが知られているのに,遙かに性能の低いアルゴリズムで車輪の再生産をする.
- ライブラリの使い方が間違ってる.
- コメントが間違っている.或いはない.
- ドキュメントが間違っている.或いはない.
- コピペする.それも汚いコードを大量に.
- コピペしたコードを編集する.コピペしてても,それらが元のまま完全に一致していれば,あとからそれらを一つのモジュールに纏め直すこともできるが,微妙に異なるためにそれができない.
- 条件分岐が間違ってる.或いは無駄に複雑.
- 変数名が間違ってる.不適切だったり,誤訳してたり,スペルや意味が間違っていたり,もちろん一貫性もない.
- モジュール分け,クラス分けが間違ってる.依存関係が間違ってる.
- 継承やデザインパターンの使い方が間違ってる.
- メソッド名が間違ってる.機能が間違ってる.戻り値が間違ってる.
これでもごく一部でまだまだ書き足りない.ごく何でもないコードですら,間違いだらけで解読不能になるのがヘッポコプログラマーの特徴だ.*12
これに対して一流プログラマの方は間違いが少ない.
一つの問題に対して一つのコードがあり,ほぼそれが正解だ.あとはそのコードをコードの書いてある通りに,そのまま理解すればいいだけ.*13
ヘボプログラマーは,一つの問題に対して似て非なるコードが三つも四つもある.「意味不明の暗号A,B,C,Dの中で,正しい意味なのはどれか答えなさい」という問題を毎日解かされているような物だ.そして「正解はそのどれでもないZでした!」となることもよくある.三つの中に正解が含まれてる保証はない.
糞コードでは複数の似て非なるコードに対して,コードに書いてないことを読み取って理解しなければ直せない.一方で一流が書いたキレイななコードなら,こういうことはない.どちらが楽かは言うまでもないだろう.
*2:バカはそもそもそんな単語すら知らないし,なにが分からないかすら分からない.
*3:天才が作って保守しにくいコードって,天才料理人が作ったマズメシくらいに有り得ない話だ.それは天才ではなく,定義からしておかしい.
*4:さらにその間違った呼び出しコードをアチコチにコピペするとか.
*5:だいたい、普通は天才だったら,その天才開発者本人にその後の保守も改良も任せるだろう...それをやってないというのは,組織としての問題.
*6:わざわざマイナーフレームワークを採用していて.その採用理由が「日本語ドキュメントがあるから」が失敗パターンの一つ.日本語ドキュメントの有無より,英語資料の豊富さを見ろ.既に豊富な英語資料があることが,成功しているフレームワークの指標の一つだ.自分達が巨人の肩に乗るつもりの小人なら英語資料は必用.
*7:そして天才なら,必用なドキュメントの大半が,ソースコード中に含まれている.
*8:その辺を理解してない管理職を相手にすると,こういうコードを書く優秀なプログラマほど貧乏くじを引かされる.難しい事をしてるんだから,あんたらに理解出来ないのは当たり前だろうに.
*9:中味は同じ.
*10:こういう糞コードは,同じコードがコピペされてるだけで,行数はだけは多いけれど実際のコード量はごくわずかな場合がある.天才が作った千行のコードは,凡才が作った1万行のコードに勝ることがある.「天才のコードを解析するのに,同じ行数の凡才のコードより時間がかかる」というのは不当な批判も見られるような気がする.
*11:同適型言語でも型の概念はあるし,使いこなす必用はあるので注意.
*12:以前,あるべきオブジェクト指向の形として「二郎チョモランマではなくにぎり寿司を目指せ」という比喩を使ったことがあるが,ヘッポコプログラマが作ったコードはにぎり寿司ではなくちらし寿司になってる.消費する分には問題ないが,仕様変更が入ると地獄だ.たとえば「海老アレルギーなので海老を抜いて下さい」と言われたらどうする?
*13:さらに実際には,コメントや変数名,クラス定義やデザパタなども適切に使用されていることが多い.読みやすさは雲泥の差だ.