リーダブルコード ―より良いコードを書くためのシンプルで実践的なテクニック (Theory in practice)
コメントの目的は、書き手の意図を読み手に知らせることである。
コードからすぐにわかることをコメントに書かない。
下記はその悪い例
// Account クラスの定義 class Account { public: // コンストラクタ Account(); // profit に新しい値を設定する void SetProfit(double profit); // この Account から profit を返す double GetProfit(); }
優れたコメントというのは「考えを記録する」ためのものである。コードを書いているときに持っている「大切な考え」のことだ。
映画のDVDにはよく「監督のコメンタリー」がついてくる。映画の製作者が自分の考えや物語について語ってくれるので、作品がどのように作られたのかを理解するのに役立つ。これと同じように、コメントにはコードに対する大切な考えを記録しなければならない。
例えば、こんな感じだ。
// このデータだとハッシュテーブルよりもバイナリツリーのほうが40%速かった。 // 左右の比較よりもハッシュの計算コストのほうが高いようだ。
// このクラスは汚くなってきている。 // サブクラス `ResourceNode` を作って整理したほうがいいかもしれない。
コードは絶えず進化しているので、その過程で欠陥を生む運命にある。その欠陥を文書化することを恥ずかしがってはいけない。例えば、改善が必要なときは以下のように書いておこう。
// TODO: もっと高速なアルゴリズムを使う
// TODO: JPEG 以外のフォーマットに対応する
記法 | 典型的な意味 |
---|---|
TODO: | あとで手をつける |
FIXME: | 既知の不具合があるコード |
HACK: | あまりキレイじゃない解決策 |
XXX: | 危険! 大きな問題がある |
定数を定義するときには、その定数が何をするのか、なぜその値を持っているのかという「背景」が存在する場合が多い。
const image_quality = 0.72; // 0.72 ならユーザはファイルサイズを品質の面で妥協できる
本書で使っている技法は、他の人にコードがどのように見えるかを想像するものだ。「他の人」というのは、プロジェクトのことを君のように熟知していない人のことである。
// このファイルには、ファイルシステムに関する便利なインターフェースを提供するヘルパー関数が含まれています。
例えば、ある関数を作っていて、「ヤバい、これはリストに重複があったら面倒なことになる」と思ったとする。それをそのまま書き出せばいい。
// ヤバい、これはリストに重複があったら面倒なことになる ↓↓↓ 言い回しをもっと詳細な言葉に置き換えるともっといい // 注意:このコードはリストの重複を処理できません(実装が難しいので)。
コメントを書くという作業の手順は以下3つに分解できる。
- 頭のなかにあるコメントをとにかく書き出す。
- コメントを読んで(どちらかと言えば)改善が必要なものを見つける。
- 改善する
ここは具体例多くあまり話入ってこなかったのでまとめだけ
- 複数のものを指す可能性がある「それ」や「これ」などの代名詞を避ける。
- 関数の動作はできるだけ正確に説明する。
- コードの意図は、詳細レベルではなく、高レベルで記述する。
条件やループなどの制御フローはできるだけ「自然」にする。コードの読み手が立ち止まったり読み返したりしないように書く。
if (length >= 10) // または if (10 <= length)
最初のほうが読みやすいが、それはなぜか?
左側 | 右側 |
---|---|
「調査対象」の式。変化する。 | 「比較対象」の式。あまり変化しない。 |
英語の用法と同じで、
自然
不自然
この自然な用法に従ってコードも書くと理解がしやすい。
if/else
ブロックの並び順if (a == b) { // 第1のケース } else { // 第2のケース }
と
if (a != b) { // 第2のケース } else { // 第1のケース }
と書くのは同じことだが、この並び順には優劣がある。
- 条件は否定形よりも肯定形を使う。例えば、
if (!debug)
ではなく、if (debug)
を使う。- 単純な条件を先に書く。
if
とelse
が同じ画面に表示されるので見やすい。- 関心を引く条件や目立つ条件を先に書く。
この優劣は衝突することもあるので、そのときは自分で判断しなければいけない。でも、優先度は明確に決まることが多い。
行数を短くするよりも、他の人が理解するのにかかる時間を短くする
基本的には
if/else
を使おう。三項演算子はそれによって簡潔になるときにだけ使おう。
第7章から第二部でコードの具体例書かれてきてだんだん理解が追いつかなくなってきました。。
最後のまとめは読めそうなので、読めそうな所だけ読むようにしたいと思います。