Java 分支構造の高度な使用法と最適化

一、高度な分岐の使用法:ネストされた分岐(if-else/switch のネスト)

ネストされた分岐は「分岐の中に分岐がある」もので、多段階の条件判断に適しています(例:ユーザー種別を判定し、その後ユーザーのレベルを判定)。企業開発では頻繁に使用されますが、読みやすさのためにネストの深さは3層までに制限することが推奨されます。

1. if-else ネストの例(ユーザ権限の判定)

public class NestedIfDemo {
    public static void main(String[] args) {
        String role = "admin"; // ロール: admin/normal
        int level = 2; // 管理者レベル: 1-3
        
        if (role.equals("admin")) {
            if (level >= 2) {
                System.out.println("上級管理者、すべての機能にアクセス可");
            } else {
                System.out.println("一般管理者、基本機能のみアクセス可");
            }
        } else if (role.equals("normal")) {
            System.out.println("一般ユーザー、バックエンドへのアクセス不可");
        } else {
            System.out.println("未知のロール、権限チェック失敗");
        }
    }
}

**企業規範**: ネストされた分岐は最大3層まで。それ以上の場合、メソッドに分割する(例:`checkAdminLevel(int level)`)。

2. switch ネストの例(注文ステータス + 支払い方法の判定)

public class NestedSwitchDemo {
    public static void main(String[] args) {
        String orderStatus = "PAID"; // 注文ステータス: UNPAID/PAID/CANCEL
        String payType = "WECHAT"; // 支払い方法: ALIPAY/WECHAT
        
        switch (orderStatus) {
            case "PAID":
                switch (payType) {
                    case "ALIPAY":
                        System.out.println("支付宝支付,已入账");
                        break;
                    case "WECHAT":
                        System.out.println("微信支付,已入账");
                        break;
                    default:
                        System.out.println("未知支付方式,需核对");
                }
                break;
            case "UNPAID":
                System.out.println("订单未支付,提醒用户付款");
                break;
            default:
                System.out.println("订单状态异常");
        }
    }
}

二、JDK 14+ の新機能:switch 式(企業での主流の新しい使用法)

従来の switch 文は「文」(戻り値なし)でしたが、JDK 14 から switch 式(戻り値あり)がサポートされました。より簡潔で、break を忘れにくいです。

1. コア文法(従来の switch との比較)

従来の switch(文) switch 式(JDK14+)
break 必須、なければ貫通 自動終了、break 不要
戻り値なし、コード実行のみ 戻り値あり、変数に直接代入可能
文法が複雑 矢印文法 `->` サポート、簡潔

2. 実践例:月から季節を取得(switch 式)

public class SwitchExpressionDemo {
    public static void main(String[] args) {
        int month = 4;
        
        // 従来の switch(break 必須)
        String season1;
        switch (month) {
            case 1: case 2: case 12:
                season1 = "冬季";
                break;
            case 3: case 4: case 5:
                season1 = "春季";
                break;
            default:
                season1 = "未知月份";
        }
        
        // switch 式(JDK14+、簡潔、break 不要)
        String season2 = switch (month) {
            case 1, 2, 12 -> "冬季";
            case 3, 4, 5 -> "春季";
            case 6, 7, 8 -> "夏季";
            case 9, 10, 11 -> "秋季";
            default -> "未知月份";
        };
        
        System.out.println("传统switch:" + season1); // 春季
        System.out.println("switch表达式:" + season2); // 春季
    }
}

3. 高度な使用法:yield キーワード(式内の複雑な論理)

public class SwitchYieldDemo {
    public static void main(String[] args) {
        int score = 88;
        String grade = switch (score / 10) {
            case 10, 9 -> "A";
            case 8 -> {
                System.out.println("成绩良好,等级B");
                yield "B";
            }
            case 7, 6 -> "C";
            default -> "D";
        };
        System.out.println("成绩等级:" + grade); // B
    }
}

三、企業レベルの分岐の最適化技術(初心者必見)

1. 複数条件の if-else → Map に置き換え(列挙 / 定数マッピング)

import java.util.HashMap;
import java.util.Map;

public class IfToMapDemo {
    private static final Map STATUS_MAP = new HashMap<>();
    static {
        STATUS_MAP.put(200, "成功");
        STATUS_MAP.put(400, "参数错误");
        STATUS_MAP.put(500, "服务器异常");
    }

    public static void main(String[] args) {
        int code = 200;
        
        String msg1;
        if (code == 200) {
            msg1 = "成功";
        } else if (code == 400) {
            msg1 = "参数错误";
        } else if (code == 500) {
            msg1 = "服务器异常";
        } else {
            msg1 = "未知状态";
        }
        
        String msg2 = STATUS_MAP.getOrDefault(code, "未知状态");
        
        System.out.println(msg1); // 成功
        System.out.println(msg2); // 成功
    }
}

2. 複雑な条件 → メソッドに分割(可読性の向上)

public class ConditionSplitDemo {
    public static void main(String[] args) {
        int score = 85;
        int type = 1; // 1=期末考,2=模拟考
        
        if (score >= 60 && score <= 100 && type == 1) {
            System.out.println("期末考及格");
        }
        
        if (isFinalExamPass(score, type)) {
            System.out.println("期末考及格");
        }
    }
    
    private static boolean isFinalExamPass(int score, int type) {
        return score >= 60 && score <= 100 && type == 1;
    }
}

3. 早期 return(else 層の削減)

public class EarlyReturnDemo {
    public static String checkUser(String username, String password) {
        if (username == null || username.isEmpty()) {
            return "用户名不能为空";
        }
        if (password == null || password.length() < 6) {
            return "密码长度不能小于6位";
        }
        return "用户校验通过";
    }

    public static void main(String[] args) {
        System.out.println(checkUser("zhangsan", "123456")); // 用户校验通过
        System.out.println(checkUser(null, "123456")); // 用户名不能为空
    }
}

四、初心者のよくある落とし穴(企業面接 / 開発でよく問われる)

1. switch の「貫通問題」(従来の switch での必須注意点)

public class SwitchPenetrationDemo {
    public static void main(String[] args) {
        int num = 1;
        switch (num) {
            case 1:
                System.out.println("执行case1"); // 会执行
            case 2:
                System.out.println("执行case2"); // 漏break,也会执行(穿透)
            default:
                System.out.println("执行default");
        }
    }
}
// 输出:
// 执行case1
// 执行case2
// 执行default

**避坑**:従来の switch では各 case の末尾に break を追加する必要がある;JDK14+ では switch 式を使用して自動的に回避。

2. if 条件の「定数を左側に置く」(空ポインタ例外の回避)

public class IfNpeDemo {
    public static void main(String[] args) {
        String name = null;
        
        if (name.equals("zhangsan")) {
            System.out.println("匹配");
        }
        
        if ("zhangsan".equals(name)) {
            System.out.println("匹配");
        }
    }
}

3. 浮動小数点数の switch 使用禁止(文法エラー)

public class SwitchFloatError {
    public static void main(String[] args) {
        double num = 1.0;
        
        if (num == 1.0) {
            System.out.println("1.0");
        }
    }
}

五、分岐構造の完全な使用ルール(まとめ)

  1. 単純な条件判定 → 単一の if/if-else(例えば、2つの選択肢、範囲判定)
  2. 固定値のマッチ(少量)→ 従来の switch(JDK14-)/switch 式(JDK14+)
  3. 固定値のマッチ(大量)→ 多重の if-else/switch に代わる Map マッピング
  4. 多段階の条件 → ネストされた分岐(最大3層)、それ以上はメソッドに分割
  5. 複雑な条件 → 読みやすいようにメソッドに分割し、早期 return で else 層を削減
  6. 避けるべき落とし穴:switch には break を追加、if では定数を左側に置く、浮動小数点数は switch で使わない、ネストは3層以内

タグ: Java if-else switch JDK14 分支优化

6月5日 23:11 投稿