【第1部】 ifのネストはもうやめよう。ガード節で可読性を劇的に改善するテクニック

この記事は、保守性の高いコード設計シリーズの一部です。これまでの記事では、クラス設計の原則について探求してきました。今回は、プログラミングの最も基本的な要素である「条件分岐」に焦点を当て、その可読性を損なう最大の要因である「ネスト」の問題を解決します。

こんにちは。if文が何重にも入れ子(ネスト)になったコードを読んで、頭が混乱した経験は誰にでもあるでしょう。インデントが深くなるにつれて、コードは右へ右へと追いやられ、どこで何をしているのかを把握するのが非常に困難になります。

このような「ネストの闇」は、コードの可読性を著しく低下させ、バグの温床となります。今回は、この問題を解決する非常にシンプルで効果的なテクニック、**ガード節(Guard Clauses)**をご紹介します。

目次

ネストしたif文がもたらす可読性の低下

ユーザーが記事を投稿できるかチェックするロジックを例に考えてみましょう。

【Before】条件が増えるたびにネストが深くなっていくコード

void postArticle(User user, Article article) {
    // ネスト1: ユーザーが有効か?
    if (user.isActive()) {
        // ネスト2: 投稿権限があるか?
        if (user.hasPostingAuthority()) {
            // ネスト3: 記事の内容が健全か?
            if (article.isAppropriate()) {
                // 本来やりたい、メインの処理
                database.save(article);
                System.out.println("投稿が完了しました。");
            }
        }
    }
}

このコードの本当に重要な処理は、一番奥深くにあるdatabase.save(article);です。しかし、そこにたどり着くまでには3つの条件をクリアしなければならず、メインの処理がどこにあるのか一目で分かりません。

解決策:ガード節でネストを解消する

ガード節とは、**「処理を続行できない異常系(または前提)の条件をメソッドの先頭でチェックし、条件に合致したら即座に処理を中断(return)する」**という書き方です。これにより、メインの処理をネストの奥深くから解放することができます。

【After】ガード節によって、平坦で読みやすくなったコード

void postArticle(User user, Article article) {
    // ガード節1: ユーザーが有効でなければ、処理を中断
    if (!user.isActive()) return;

    // ガード節2: 投稿権限がなければ、処理を中断
    if (!user.hasPostingAuthority()) return;
    
    // ガード節3: 記事の内容が不健全なら、処理を中断
    if (!article.isAppropriate()) return;

    // すべてのチェックを通過した後の、メインの処理
    // ネストがなく、インデントも浅い!
    database.save(article);
    System.out.println("投稿が完了しました。");
}

いかがでしょうか。異常系の条件はすべてメソッドの冒頭にまとめられ、「事前チェック」の役割を担っていることが明確になりました。そして、その後に続くのが本来の正常系の処理です。コードが上から下へまっすぐに読めるようになり、可読性は劇的に向上しました。条件の追加や、メイン処理の追加も非常に簡単です。


else句もガード節で解消できる

この早期returnのテクニックは、if-else if-elseの連鎖を解消するのにも役立ちます。

【Before】else句が多く、やや冗長なコード

UserStatus getUserStatus(User user) {
    UserStatus status;
    if (user.isDeleted()) {
        status = UserStatus.DELETED;
    } else if (user.isSuspended()) {
        status = UserStatus.SUSPENDED;
    } else if (user.isActive()) {
        status = UserStatus.ACTIVE;
    } else {
        status = UserStatus.INACTIVE;
    }
    return status;
}

【After】早期returnelse句をなくした、スッキリしたコード

UserStatus getUserStatus(User user) {
    if (user.isDeleted()) return UserStatus.DELETED;
    if (user.isSuspended()) return UserStatus.SUSPENDED;
    if (user.isActive()) return UserStatus.ACTIVE;

    return UserStatus.INACTIVE;
}

elseが不要になり、各条件が独立して評価されるため、非常にシンプルで読みやすいコードになりました。

まとめ

if文のネストは、コードの可読性を損なう主要な原因の一つです。 「異常な条件や前提条件は、メソッドの冒頭でガード節を使って早期returnする」 このシンプルなルールを適用するだけで、あなたのコードはより平坦で、理解しやすく、メンテナンスしやすいものに生まれ変わるでしょう。

▼次の記事 次回は、もう一つの厄介な条件分岐であるswitch文に焦点を当てます。複数の場所に同じswitch文が重複することで発生する問題と、それをオブジェクト指向の強力な武器「ポリモーフィズム」で解決するストラテジーパターンを解説します。

【第2部】 switch文の増殖はバグの温床。ストラテジーパターンで条件分岐を撲滅する

よかったらシェアしてね!
  • URLをコピーしました!
  • URLをコピーしました!

この記事を書いた人

私が勉強したこと、実践したこと、してることを書いているブログです。
主に資産運用について書いていたのですが、
最近はプログラミングに興味があるので、今はそればっかりです。

目次