なぜ読みやすいコードが必要なのか - コードの可読性を高める手法をサンプルで学ぶ
システム開発会社「アクシア」の代表として、自社・他社含め、さまざまなエンジニアのコードを読んできた米村歩さん。そんな米村さんの持論は、「コードの可読性は生産性に多大な影響を与える」ということ。可読性の低いコードはどんな弊害をもたらし、どうすれば改善できるのか――。チーム開発を効率化するコードの「可読性」について綴っていただきました。
プロフェッショナルのエンジニアには、「可読性」の高いコードを書くスキルは必要不可欠です。単に目的とする処理が実行できればよいわけではありません。しかし実際の開発業務の中では、可読性は意外と軽視されてしまいがちです。
経験の浅い駆け出しのエンジニアにとっては、可読性の重要さを肌感覚で理解するのは難しいかもしれません。また、新人エンジニアに対してプログラミング言語や開発ツールについての指導が行われることはあっても、コードの可読性がなぜ重要なのか――その理由が具体的に説明されないケースもあるでしょう。
そこで本稿では、コードの可読性がなぜ重要なのか、可読性の高いコードを書くことでどんなメリットが得られるのか、具体的なイメージができるように解説していきます。
コードの可読性が生産性を左右する
そもそもの問題として、コードの可読性はなぜ軽視されてしまうのでしょうか。それは、コードの可読性が低くてもプログラムは動作するからです。
私も一人のエンジニアとして感じるのですが、コードの可読性にまったく関心がないというエンジニアはいないと思います。しかし実際の開発現場では、仕事をともにするプロジェクトマネージャーや顧客がコードを読めない、というケースは当たり前にあります。こうしたプログラムのソースコードを読めない人にとって、関心の対象は目的通りに処理が実行されるかどうかが主であり、コードの可読性ではありません。
つまり、プログラムが正しく動かない場合には上司や顧客から指摘を受けるが、たとえ読みにくいコードを書いても何のお咎めもない、ということが起きうるのです。
もちろん一般的な開発チームであれば、作成したコードをチェックするコードレビューというフェーズを通るので、この段階で可読性の低いコードには指摘が入ります。ところが納期が迫っていたりプロジェクトが炎上していたりすると、「とりあえずプログラムが動くこと」が優先され、コードの可読性の優先順位が下げられてしまうことは現実問題として発生しえます。
しかしコードの可読性を犠牲すると、さまざまな問題が発生します。その最たるものが生産性の低下です。コードの可読性を向上させることは決してエンジニアの自己満足ではありません。チームとしての生産性を高めるうえで重要な要素なのです。
生産性とはすなわち、会社の売上であり、利益であり、従業員の業務時間であり、給料です。生産性が上がればこれらの数値は改善しますが、生産性が下がれば当然逆の結果となります。生産性は、会社はもちろんのこと、エンジニア一人ひとりにとっても重要な指標です。その生産性に大きな影響を与えるからこそ、コードの可読性はもっと重視されるべきなのです。
コードは人に読まれるもの
私は、プログラムを書くという行為には、大きく分けて次の2つの目的があると考えています。
- 目的の処理を実行する
- 人間が読む
1つ目は「目的の処理を実行する」ことです。ここでいう「目的の処理」には、プログラムが仕様通りの動きをするのはもちろんのこと、十分な処理速度で動作するといったパフォーマンス面の要求も含まれます。プログラムが仕様通りの動きをしていなければ、プログラムを書く目的が果たされているとは言えません。
もう1つ、忘れてはならない目的として挙げられるのが、「プログラムは人間が読む」という点です。プログラムは書かれたその瞬間から不特定多数のエンジニアに「読まれるもの」となります。可読性が低く読みにくいコードは、実装後の工程で生産性を低下させてしまうのです。
システム開発では、コードを書いたあとには、次のような工程が待っています。
- レビューをする
- テストをする(テストコードを書く)
- バグの原因を見つける
- バグを改修する
- 仕様を変更する
- 機能を追加する
- 性能を改善する
- 流用する
これらすべての工程で「読む」というアクションが発生します。プログラムは書く時間よりも読まれる時間のほうが圧倒的に長いのです。可読性の低いコードを書くということは、上記すべての工程の生産性を下げてしまうこととイコールです。そして、コードを書いた本人はもちろん、他者が読むこともある、と強く認識しておく必要があります。コードを書いた本人は内容を把握していると思いますが、他のエンジニアも1行1行読んで内容を理解していく必要があり、可読性の低いコードは理解するにに時間がかかってしまうのですから。
生産性を高めるためには、「目的の処理を実行する」という目的が果たされている範囲内で、できるだけ早く実装する必要があります。しかし単に早く実装することだけが生産性向上に寄与するわけではありません。長い目でシステム開発を見たときに、生産性を高めるためには、保守性を高くすることも重要です。そして保守性を高める要素の1つが可読性なのです。
「早く実装する」と「保守性を高くする」という2つの取り組みは以下のようなマトリクスに整理できるでしょう。
「早く実装する」は緊急性が高く重要な課題です。それに対して「保守性を高くする」は緊急でありませんが重要な課題です。ついつい緊急で重要な課題に目がいってしまいがちですが、長期的に見てより重要なのは「緊急ではないが重要な課題」、つまり保守性を高くすることです。
可読性が低いコードがもたらす弊害
コードの可読性が低いと、生産性の低下を招くということはおわかりいただけたかと思います。この弊害をもう少し細分化してみると、以下の4つの問題に分類できます。
- プログラムを読む時間がかかる
- バグが混入しやすくなる
- バグの原因特定に時間がかかる
- 改修に時間がかかる
前述の通り、コードは最初に書かれた後さまざまな工程で読まれることになりますが、そのすべての工程で余計な時間が発生します。また読みにくいコードにはバグが混入しやすくなり、その原因の特定や改修にもより多くの時間がかかってしまいます。
自分が想像している以上に、自分の書いたコードはさまざまな場面で読まれることになります。最初に可読性の低いコードを書いてしまうと、長期的な負の資産となって生産性を落とし続けることになってしまいます。
コードの可読性を高めるためには?
では、コードの可読性を高めるためには具体的に何に気を付ければよいのでしょうか。
シンプルイズベスト
複雑なコードであればあるほど読みにくくなるので、コードの可読性を高めるためには基本的にはシンプルな記述を心がけるべきでしょう。ただし注意していただきたいのは、前述した通りプログラムには「目的の処理を実行する」と「人間が読む」の2つの目的があるということです。
「目的の処理を実行する」という目的には、パフォーマンス面の問題も含まれます。システム開発をしていると、プログラム処理のパフォーマンスを優先するために可読性を犠牲にするという状況は十分に考えられます。一方で、パフォーマンスがそれほど重要ではない処理であれば、多少のパフォーマンスを犠牲にして可読性を優先するという判断もありえます。
同じエンジニアであっても、仕事上の価値観は個々人で異なります。パフォーマンスを重視する人もいれば、逆に可読性を重視する人もいます。しかしこれら2つはどちらか一方だけが正しいというものではなく、目的が違うということを理解する必要があります。パフォーマンスと保守性のどちらを優先するのかによって、方針を決定するべき問題です。
オリジナリティを発揮してはならない
プログラムを書くときにはオリジナリティを発揮してはいけません。これが、同じ読み物であっても、プログラムと自然言語の異なるところです。プログラムは芸術作品ではありません。難解な変数名や処理を書いてわざわざ読む人に余計なことを考えさせるメリットはありません。
また、プログラムはできるだけわかりやすくダイレクトに伝わる書き方を心がけるべきです。まるで暗号文のような複雑怪奇なプログラムをときおり見かけますが、このようなプログラムは生産性を低下させ、バグを混入させやすくなるだけです。
プログラムは人に何かを伝えるために書く文章と同じです。自分だけのオリジナリティにあふれたコードを書く必要はまったくありません。むしろ一般的ではないオリジナリティに富んだ書き方は、ただ読みにくくて可読性が低いだけのコードを生んでしまうため、厳に慎むべきです。
コードを読みにくする要因と、その解決策を学ぶ
ここからは、具体例を交えて可読性の低いコードと、それを改善する方法を解説していきます。サンプルコードも提示しますので参考にしてみてください。
コードが長すぎる
長すぎるコードは可読性を低下させます。1つのクラスやメソッドが必要以上に長くなりすぎないように適切に分割するべきです。1つのクラスの長さが数千行にも及ぶようなコードはそれだけで生産性を低下させてしまう可能性が高いです。1メソッドは、画面スクロールをしないで済む程度が読みやすいでしょう。
条件式が長すぎる
条件式も可読性が低下してバグが混入しやすくなります。以下は条件式が長すぎる例です。
以下のように条件式の内容をメソッドに分割するなど工夫することで、可読性を高めることができます。条件式を短くすることで、テストコードが書きやすくなるというメリットもあります。
ネストが深すぎる
条件式が長すぎる場合と同様、ネストが深くなりすぎている場合にも、可読性が低下してバグが混入しやすくなります。以下をご覧ください。
こうした場合もメソッドを分割するなどの方法で可読性を高めることができます。
マジックナンバーが使われている
以下例示のようにプログラムを書いている本人にとっては自明でも、あとから読んだ人はマジックナンバーが何を意味しているのか理解するのは困難です。また、同じ意味のマジックナンバーが複数箇所で使用されていると、数値が変更になったときに使用箇所を洗い出す必要があります。
数値には以下のように適切な変数名を付けて、あとで見たときに何を表しているのかを理解しやすいようにし、使い回しやすい形にすべきです。
変数名やメソッド名が不適切
変数名やメソッド名は、その内容が何を表しているのかを表現するための重要な要素です。この名称が不適切だと、あとで読んだときに誤った読み方をしてしまうリスクがあるため、変数名やメソッド名はわかりやすく適切な名称にするべきです。以下の例を見てください。
- check() - abc() - name
これは不適切な命名の例です。 check
だけではなにをチェックするのか不明瞭です。 abc
はそもそも意図も意味も伝わりません。name
は名前ということは分かりますが、どんな名前が入るのかは判別できません。名前と言ってもユーザー名や人名、ニックネーム、会社名などが挙げられます。命名はその名を目にした人が、直感的に処理内容をイメージできる必要があります。以下の例を見てください。
- checkUserStatus() - createMessage() - userName
このように、変数やメソッドがどのような処理を行うのかを考慮し、明示的に命名することが、読みやすく保守性の高いコードにつながります。
コメントが不適切・ノーコメント
コードに対して読みやすいようにコメントを付けることがありますが、コメントは多すぎても少なすぎてもわかりにくくなってしまいます。もちろんコメントの内容が間違っているのは論外です。コメントの内容を信じて実装してしまった人が不要なバグを発生させてしまうリスクが高まってしまいます。特にコードを修正した際には該当するコメントも適切に修正するように注意が必要です
また、コードを読めばわかるからコメントは不要という考え方もありますが、可読性の重要性を理解していればコメントの重要性は理解できるはずです。もっとも、コメントは重要ですが“コードを読めば瞬時に誰もが理解できる内容”をわざわざコメントにするのもよくありません。逆に可読性を低下させてしまいます。
以上、解説してきた通り、コードの可読性は生産性に大きな影響を与えることは明らかです。今後のプログラミングスキルの習得や後進の指導に、この記事の内容が少しでも参考になることを願っています。
米村 歩 yonemura2006
編集:内形 文(リブロワークス)