概述:
在 Java 中,枚举(Enum)就是一个可以表示穷尽罗列的类,当一个类的对象只有有限个、确定个的时候,我们就可以定义一个枚举类来存放这些对象。
枚举的每个值都是这个枚举类型的唯一实例。它还可以包含方法、构造器和属性,可以看作是功能丰富的类。
枚举的特点
- 枚举类型是常量的集合:枚举中的每个值是常量,且不可更改。
- 每个枚举值都是唯一的:每个枚举值都是该枚举类的一个实例,且是单例的。
- 枚举可以有属性和方法:可以为枚举添加属性和行为。
- 隐式继承
java.lang.Enum
:所有枚举都继承自java.lang.Enum
类,不能再继承其他类。 - 线程安全:枚举实例是线程安全的,因为它们是不可变的常量。
为什么需要枚举类?
可以在编译时避免一些不合法的对象,如:
int day = 0; // 假设 day 的值为 0
if (day == Weekday.MON) {
System.out.println("今天星期一");
}
枚举的定义
在下面的例子中,
Day
是一个枚举类型,定义了一周中的 7 天作为常量public enum Day { MONDAY, TUESDAY, WEDNESDAY, THURSDAY, FRIDAY, SATURDAY, SUNDAY }
使用枚举
public class TestEnum { public static void main(String[] args) { Day today = Day.MONDAY; switch (today) { case MONDAY: System.out.println("Start of the week."); break; case FRIDAY: System.out.println("End of the week."); break; default: System.out.println("Midweek."); break; } } }
使用
switch
语句来检查today
的值,它是Day
枚举的一个实例。如果将
today
的值修改为0
,会在编译时报错。(today
的类型是Day
枚举类型,而0
是一个整数(int
),不能直接赋值给Day
类型。)
使用带属性的枚举
在下面的例子中,定义了一个
Status
枚举类型,其中每个枚举值都包含了两个属性code
和message
,并且提供了一个构造器来为每个枚举值初始化这些属性。public enum Status { SUCCESS(200, "Success"), ERROR(500, "Error"), NOT_FOUND(404, "Not Found"); private int code; private String message; Status(int code, String message) { this.code = code; this.message = message; } public int getCode() { return code; } public String getMessage() { return message; } }
使用带属性的枚举
public class TestEnumWithAttributes { public static void main(String[] args) { Status status = Status.SUCCESS; System.out.println("Code: " + status.getCode()); System.out.println("Message: " + status.getMessage()); } }
输出:
Code:200
Message:Success
枚举的方法
values()
:返回枚举类型的所有常量值。
valueOf(String name)
:根据给定的名称返回对应的枚举常量。如果传入的名称不匹配,将抛出 IllegalArgumentException
。
Day day = Day.valueOf("MONDAY");
ordinal()
:返回枚举常量的顺序(从 0 开始计数)
System.out.println(Day.MONDAY.ordinal()); // 输出 0
name()
:返回枚举常量的名称(字符串形式)。
System.out.println(Day.MONDAY.name()); // 输出 "MONDAY"
枚举的优点
-
类型安全:
- 枚举可以确保只使用预定义的常量,而不是使用其他值或错误的字符串。
-
增强可读性:
- 使用枚举代替魔法值(如整数或字符串)可以提高代码的可读性和维护性。
-
功能丰富:
- 枚举不仅可以表示常量,还可以封装更多的逻辑(如带有属性、方法)。
-
统一管理常量:
- 与传统的
public static final
常量相比,枚举将相关常量集中管理,提高了代码的组织性。
- 与传统的
枚举的应用场景
-
状态机:
- 枚举常用于表示不同的状态,如请求的状态(成功、失败、处理中等)。
-
选项或配置:
- 使用枚举来定义选项、配置或模式类型,例如线程池策略、颜色选择等。
-
枚举单例:
- 枚举类型可以用来实现单例模式,因为它天然是单例的
- 枚举单例的例子
-
public enum Singleton { INSTANCE; public void show() { System.out.println("This is a singleton."); } } public class TestSingleton { public static void main(String[] args) { Singleton instance = Singleton.INSTANCE; instance.show(); } }