侧边栏壁纸
博主头像
星空之窗

学如逆水行舟,不进则退。

  • 累计撰写 5 篇文章
  • 累计创建 17 个标签
  • 累计收到 4 条评论

目 录CONTENT

文章目录

浅浅了解 Java 中的 switch

星河景明
2025-03-27 / 0 评论 / 0 点赞 / 9 阅读 / 0 字 / 正在检测是否收录...
温馨提示:
部分素材来自网络,若不小心影响到您的利益,请联系我们删除。

浅浅了解 Java 中的 switch

Coding 时正好遇到了一个 switch 的高版本特性,以前没见过,就正好兴致来了去简单了解下 switch 随着 Java 版本更新的变化。

Java 1.0 至 Java 4: 传统 switch 语句的基础支持

支持类型: 仅限整型 (byteshortint) 和字符型 (char)

switch (expression) {
    case value1:
        // 代码块
        break;
    case value2:
        // 代码块
        break;
    default:
        // 默认代码块
}

特性限制:

  • 必须显式使用 break 防止贯穿 (fall-through)
  • case 值需为编译时常量,且不可重复
  • 无法处理字符串或复杂对象

Java 5

新增支持: 允许 case 标签使用枚举常量

意义: 增强类型安全性, 避免魔法值

enum Day { MONDAY, TUESDAY, WEDNESDAY }
Day day = Day.TUESDAY;
switch(day) {
    case MONDAY:
        System.out.println("Monday");
        break;
    case TUESDAY:
        System.out.println("Tuesday");
        break;
    default:
        System.out.println("Other day");
}

Java 7

新增支持:支持字符串类型包装类(Byte, Short, Character, Integer)

String fruit = "apple";
switch(fruit) {
    case "apple":
        System.out.println("Apple is red.");
        break;
    case "banana":
        System.out.println("Banana is yellow.");
        break;
    default:
        System.out.println("Unknown fruit.");
}

实现原理:

  • 通过调用 hashCode() 将字符串转换为整型, 再通过 equals() 验证匹配, 确保唯一性

  • 反编译示例:

    switch(fruit.hashCode()) {
        case 99162322:
            if (fruit.equals("apple")) { /* case代码 */ }
            break;
        // ...
    }
    

注意事项:

  • 区分大小写,依赖 equals() 的精确匹配
  • 性能略低于整型 switch, 但可读性显著提升

Java 12

语法革新:

  • 箭头语法 (->) : 替代 break, 避免贯穿问题
  • 多值匹配: 允许逗号分隔多个 case
  • 表达式化: switch 可作为表达式返回值
  • 通过 break 关键字返回值

通过 break 关键字返回值例子

return switch (day) {
    case "Monday":
        break "Weekday";
    case "Tuesday":
        break "Weekday";
    case "Wednesday":
        break "Weekday";
    case "Thursday":
        break "Weekday";
    case "Friday":
        break "Weekday";
    case "Saturday":
        break "Weekend";
    case "Sunday":
        break "Weekend";
    default:
        break "Unknown";
};

通过箭头运算符返回值

return switch (day) {
    case "Monday" -> "Week day";
    case "Tuesday" -> "Week day";
    case "Wednesday" -> "Week day";
    case "Thursday" -> "Week day";
    case "Friday" -> "Week day";
    case "Saturday" -> "Weekend";
    case "Sunday" -> "Weekend";
    default -> "Unknown";
};

case 中多个值的例子

return switch (day) {
    case "Monday","Tuesday","Wednesday","Thursday","Friday" -> "Week day";
    case "Saturday", "Sunday" -> "Weekend";
    default -> "Unknown";
};

Java 13

新增关键字: yield 用于从 switch 块中返回值,替代 break 结合表达式的方式

String type = switch (obj) {
    case Integer i:
        yield "整数";
    case String s:
        yield "字符串";
    default:
        yield "未知类型";
};

Java 14

标准化特性: 将 Java 12-13 的预览特性(通过标记参数 -enable-preview=true 开启)定为标准功能

Java 17 (Preview)

模式匹配: 可以在 switch 条件下传递对象,并且可以在 switch case 标签中检查该对象的不同类型, 如下面的例子:

return switch (obj) {
    case Integer i -> "It is an integer";
    case String s -> "It is a string";
    case Employee s -> "It is a Employee";
    default -> "It is none of the known data types";
};

保护模式

before:

case Employee emp:
	if(emp.getDept().equals("IT")) {
		yield "This is IT Employee";
	}

after:

return switch (obj) {
    case Integer i -> "It is an integer";
    case String s -> "It is a string";
    case Employee employee when employee.getDept().equals("IT") -> "IT Employee";
    default -> "It is none of the known data types";
};

空值处理

对于 null 的处理

static void test(Object obj) {
  switch (obj) {
    case null -> System.out.println("null!");
    case String s -> System.out.println("String");
    default -> System.out.println("Something else");
  }
}

在此预览功能之前,当 objnull 时, 此示例会抛出 NullPointerException

而在此后则是正常处理能够打印出 null!

也可以组合起来用:

static void testStringOrNull(Object obj) {
  switch (obj) {
    case null, String s -> System.out.println("String: " + s);
    default -> System.out.println("Something else");
  }
}

不过值得一提的是如果选择器表达式的计算结果为 null 并且 switch 块没有 null case 标签, 那么就会正常抛出 NullPointerException

String s = null;
switch (s) {
  case Object obj -> System.out.println("This doesn't match null");
  // No null label; NullPointerException is thrown
  // if s is null
}
0
  1. 支付宝打赏

    qrcode alipay
  2. 微信打赏

    qrcode weixin

评论区