Java枚举(enum)
Free Talk
上学期上Java课时都没有听说过枚举的概念,这次偶然在JavaGuide博客中看到了,就想写一些枚举相关知识。本篇文章会较为深入地讲解一下枚举的强大功能。
写这边博客的时候,又发现了廖雪峰的Java教程也写的很好,可以配套食用。
JavaGuide和廖雪峰
简介
Java枚举其实是指一种特殊的类,它一般用来表示一组常量。
1 | package shuang.kou.enumdemo.enumtest; |
上面的代码为了避免定义常量,将和Pizza有关的常量都放入了枚举类中。
1 | System.out.println(PizzaStatus.ORDERED.name());//ORDERED |
Why need it?
在Java中我们想要定义常量,完全可以用static final
来定义,比如我们想要定义周一到周日这几个常量。
1 | public class Weekday { |
但是当用这些常量来表示一组枚举值时,会产生一个严重的问题,编译器无法检查每个值的合理性。
1 | if (weekday == 6 || weekday == 7) { |
因此以枚举方式定义的常量使代码更具可读性,允许进行编译时检查,预先记录可接受值的列表,并避免由于传入无效值而引起的意外行为。
廖雪峰枚举
==比较
使用enum
定义的枚举类是一种引用类型。
而引用类型比较,要使用equals()
方法,如果使用==
比较,它比较的是两个引用类型的变量是否是同一个对象。因此,引用类型比较,要始终使用equals()
方法,但enum
类型可以除外。
引用类型与基本数据类型分类见下表,图片来源
这是因为enum
类型的每个变量在JVM中只有一个唯一实例,所以可以直接用==
比较。
1 | if (day == Weekday.FRI) { // ok! |
Switch语句
1 | public int getDeliveryTimeInDays() { |
enum类型
通过enum
定义的枚举类,和其他的class
有什么区别?
答案是没有任何区别。enum
定义的类型就是class
,只不过它有以下几个特点:
- 定义的
enum
类型总是继承自java.lang.Enum
,且无法被继承; - 只能定义出
enum
的实例,而无法通过new
操作符创建enum
的实例; - 定义的每个实例都是引用类型的唯一实例;
- 可以将
enum
类型用于switch
语句。(如上所示)
我们可以定义一个Color
枚举类:
1 | public enum Color { |
通过编译器编译出的class
大概就是这样:
1 | public final class Color extends Enum { // 继承自Enum,标记为final class |
所以,编译后的enum
类和普通class
并没有任何区别。但是我们自己无法按定义普通class
那样来定义enum
,必须使用enum
关键字,这是Java语法规定的。
因为enum
是一个class
,每个枚举的值都是class
实例。
常用方法
name()
返回常量名
1 | String s = Weekday.SUN.name(); // "SUN" |
ordinal()
返回定义的常量的顺序,从0开始计数
1 | int n = Weekday.MON.ordinal(); // 1 |