关键字enum 可以将一组具名的值的有限集合创建一种新的类型,而这些具名的值可以作为常规的程序使用。创建enum 时,编译器会为你生成一个相关的类,这个类继承自java.lang.Enum 。下面是一个例子演示了一些Enum 提供的一些功能。

package com.jas.enumtest;enum Animal{CAT,DOG,SHEEP}public class EnumClass {public static void main(String[] args) {for(Animal animal : Animal.values()){System.out.println(animal + " oridinal:" + animal.ordinal());System.out.print(animal.compareTo(Animal.DOG) + " ");System.out.print(animal.equals(Animal.DOG) + " ");System.out.println(animal == Animal.DOG);System.out.println(animal.getDeclaringClass());System.out.println(animal.name());System.out.println("--------分割线----------");}for(String str : "DOG,CAT,SHEEP".split(",")){Animal animal = Animal.valueOf(Animal.class,str);System.out.print(animal + " ");}}
}

输出:
CAT oridinal:0
-1 false false
class com.jas.enumtest.Animal
CAT
——–分割线———-
DOG oridinal:1
0 true true
class com.jas.enumtest.Animal
DOG
——–分割线———-
SHEEP oridinal:2
1 false false
class com.jas.enumtest.Animal
SHEEP
——–分割线———-
DOG CAT SHEEP

ordinal() 方法返回一个int 类型的值,这个值是enum 在实例中声明的顺序,从0 开始。可以使用 == 来比较enum 实例,编译器会自动为你提供equals() 方法与 hashCode() 方法。Enum 类实现了Comparable 接口,所以你可以使用compareTo() 方法。同时Enum 类还实现了Serializable 接口。
      getDeclaringClass() 方法返回其所属的类。
      name 方法返回enum 实例声明时的名字,这与toString 方法返回的值相同。valueOf() 是在Enum 中定义的static 方法,它可以根据给定的名字返回相应的enum 实例,如果不存在给定名字的实例,就会抛出异常。

覆盖enum 的方法
      当我们想要覆盖enum 中的方法时,我们会发现,它就只有一个方法toString(),当我们覆盖它时与覆盖一般的类的方法没有区别。

enum Animal{CAT,DOG,SHEEP;@Overridepublic String toString() {String id = name();String lower = id.substring(1).toLowerCase();return id.charAt(0) + lower;}
}
public class EnumClass {public static void main(String[] args) {for(Animal animal : Animal.values())System.out.print(animal + " ");}
}

输出
Cat Dog Sheep

向enum 中添加方法
      除了不能继承一个enum 之外,我们基本上可以将enum 看作是一个常规的类。这也意味着enum 拥有自己的构造函数,以及我们可以向enum 中添加方法。它甚至是可以拥有main() 方法。这里我们通过一个方法返回一个枚举类型的描述不再仅仅是一个toString() 类型的实现。

enum Animal{// private String description; 这是不允许的CAT("喵喵喵~"),DOG("汪汪汪~"),SHEEP("咩咩咩~");private String description;private Animal(String description){this.description = description;}public String getDescription(){return description;}
}
public class EnumClass {public static void main(String[] args) {for(Animal animal : Animal.values())System.out.println(animal + " : " + animal.getDescription());}
}

输出:
CAT : 喵喵喵~
DOG : 汪汪汪~
SHEEP : 咩咩咩~

需要注意的是:如果我们打算自定义方法,那么必须在enum 徐磊实例的后面添加一个分号。同时Java 要求你必须先定义enum 实例,就像上面这样我们打算在定义enum 实例之前定义description 但是却得到一个编译器的错误提示。enum 中的构造函数与方法与普通的类没有任何区别,除了有少量的限制enum 可以说就是一个类。所以我们可以使用enum 做许多额外的事。

switch 语句中的 enum
      一般来说,在switch 语句中 只能使用整数值,而枚举天生就具备整数值的次序,并且可以通过ordinal() 方法获得其在enum 中的顺序,因此我们可以在switch 中使用枚举。

enum Singal{GREEN, YELLOW, RED}public class TrafficLight {Singal color = Singal.RED;public void change(){switch (color){case RED: color = Singal.GREEN;break;case GREEN: color = Singal.YELLOW;break;case YELLOW: color = Singal.RED;break;}}public String toString(){return "The traffic light is : " + color;}public static void main(String[] args) {TrafficLight light = new TrafficLight();for (int i = 0; i < 4; i++) {System.out.println(light.toString());light.change();}}
}

输出:
The traffic light is : RED
The traffic light is : GREEN
The traffic light is : YELLOW
The traffic light is : RED

values() 的神秘之处
      我们知道编译器为我们创建的enum 都继承自Enum 类。但是如果你去查看Enum 类就会发现,它并没有values() 方法。但是我们在上面确实使用了这个方法,这是为什么呢?下面我们使用反射机制来查看其中的原因。

import java.lang.reflect.Method;
import java.lang.reflect.Type;
import java.util.Set;
import java.util.TreeSet;enum Explore{HERE,THERE}
public class Reflection {public static Set<String> analyze(Class<?> enumClass){Set<String> set = new TreeSet<>();System.out.println("----- Analyzing " + enumClass + " -----");for(Type type : enumClass.getGenericInterfaces())System.out.println("genericInterface : " + type);System.out.println("superClass : " + enumClass.getSuperclass());for(Method method : enumClass.getMethods())set.add(method.getName());System.out.println("----- end -----");System.out.println();return set;}public static void main(String[] args) {Set<String> exploreMethods = analyze(Explore.class);Set<String> enumMethods = analyze(Enum.class);System.out.println("exploreMethods : " + exploreMethods);System.out.println("enumMethods : " + enumMethods);System.out.println("exploreMethods.containsAll(enumMethods): " + exploreMethods.containsAll(enumMethods));System.out.println("exploreMethods.removeAll(enumMethods): " + exploreMethods.removeAll(enumMethods));System.out.println("exploreMethods : " + exploreMethods);}
}

—– Analyzing class com.jas.enumtest.Explore —–
superClass : class java.lang.Enum
—– end —–

—– Analyzing class java.lang.Enum —–
genericInterface : java.lang.Comparable
genericInterface : interface java.io.Serializable
superClass : class java.lang.Object
—– end —–

exploreMethods : [compareTo, equals, getClass, getDeclaringClass, hashCode, name, notify, notifyAll, ordinal, toString, valueOf, values, wait]
enumMethods : [compareTo, equals, getClass, getDeclaringClass, hashCode, name, notify, notifyAll, ordinal, toString, valueOf, wait]
exploreMethods.containsAll(enumMethods): true
exploreMethods.removeAll(enumMethods): true
exploreMethods : [values]

答案就是values() 方法是由编译器添加的static 方法。其实这个过程中还未其添加了valueOf() 方法。但是Enum 中明明已经有了valueOf() 方法,为什么编译器还会为其添加这个方法呢?Enum 中的valueOf() 方法需要传递进来两个参数,但是新增的这个方法只需要传递进来一个参数。

参考书籍:
                                                                                                                《Java 编程思想》Bruce Eckel 著 陈昊鹏 译

枚举(enum)类型相关推荐

  1. Java枚举(Enum)类型使用的正确姿势

    关于Java Enum的介绍及原理参见 Java枚举(Enum)类型的基本介绍与原理探求 Enum类型的基本使用 定义一个枚举类的主要作用就是在逻辑代码中对某个变量的值进行比较.同样以季节的枚举类Se ...

  2. Java枚举(Enum)类型的基本介绍与原理探求

    Enum枚举类型 Enum的全写是Enumeration,这个词的翻译是列举.逐条陈述.细目.在程序语言中,枚举类型是一种特殊的数据类型(常用的数据类型比如字符串.整型),这种数据类型的变量值限定在固 ...

  3. C++枚举enum类型-典型性质

    适用于大学阶段了解简单的枚举类型的特征, 如果"赶时间"可以直接跳转"特性总结". 文章目录 前言 一.使用案例 二.特性总结 1.基本类型 2.基本性质 3. ...

  4. mysql 枚举_是否推荐使用MySQL的enum类型?

    使用 MySQL ENUM 作为列的数据类型有两个主要的好处,一是使得数据更紧凑进而节省空间,二是更好的可阅读性.但是,享受这些好处的同时,也要承担 ENUM 所带来的各种负面影响. 我们罗列几个主要 ...

  5. c++ enum 给定类型_C++11作用域内枚举enum

    在C++11之前的枚举(enum),是没有办法两个枚举(enum)内有相同枚举名的.如果还不知道C++中枚举(enum)是什么,可以看这篇:枚举enum 如:苹果和桔子都有大,中,小.写个代码来说明下 ...

  6. 取枚举的参数c语言,求解:如何获得enum类型中枚举值的数量

    评论 # re: 求解:如何获得enum类型中枚举值的数量 2009-11-11 20:43 OwnWaterloo # re: 求解:如何获得enum类型中枚举值的数量[未登录] 2009-11-1 ...

  7. Typescript - enum 枚举类型(数值型枚举 / 字符串枚举 / 常量枚举 / 异构枚举 / 计算枚举成员 / 联合枚举和枚举成员类型 / 运行时的枚举 / 环境枚举 / 对象与枚举)教程

    前言 Enums(枚举)是 TypeScript 的少数功能之一,它不是 JavaScript 的类型级扩展,仅支持数字的和基于字符串的枚举. 使用枚举您可以定义一组带名字的常量,并且清晰地表达意图或 ...

  8. c语言遍历枚举,C# Enum 类型遍历

    void Main() { new EnumForeach().Foreach(); } public class EnumForeach { public void Foreach() { fore ...

  9. java 枚举型 默认值,c# - 选择Enum类型的默认值而不必更改值

    c# - 选择Enum类型的默认值而不必更改值 在C#中,是否可以使用属性修饰Enum类型或执行其他操作来指定默认值应该是什么,而不更改值? 无论出于何种原因,所需的数字可能都是一成不变的,并且仍然可 ...

最新文章

  1. 来看看C# ObservableCollection和List的区别
  2. spring-amqp整合rabbitmq消费者配置和代码
  3. Nchain旗下矿池挖出首个BCH区块,“算力战争”真的要来了?
  4. python方法测试_python 测试常用小方法
  5. 广发证券携手神策数据 多维分析满足复杂业务需求
  6. matlab选择结构
  7. 通常你会在什么地方遇到DBNull?
  8. DPM 2012 SP1---安装并部署DPM 2012 SP1服务器
  9. python中object是什么数据类型_自学Python2.1-基本数据类型-字符串str(object) 上
  10. java 冒泡排序的三种写法_冒泡排序的三种实现(Java)
  11. 新浪的动态策略灰度发布系统:ABTestingGateway
  12. ThinkPHP第十九天(Ueditor高亮插件、扩展函数载入load、静态缓存)
  13. 3D视觉——1.人体姿态估计(Pose Estimation)入门——使用MediaPipe含单帧(Signel Frame)与实时视频(Real-Time Video)
  14. 托马斯微积分是数学守旧派的代表作
  15. RAID磁盘阵列有哪几种?
  16. Java创建Shape类
  17. 关于datetimepicker 鼠标滚动调节日期变化遇到的问题
  18. Android仿iOS左右滑动开关控件(Android4.0以上适用)
  19. app抓包服务器证书错误,Fiddler抓包iOS出现证书错误的解决办法
  20. 英尺 厘米_在35,000英尺处重建747

热门文章

  1. Spring Boot-@EnableWebMvc注解
  2. 绝地求生自定义服务器租一天多少钱,绝地求生自定义服务器怎么样?绝地求生自定义服务器使用攻略...
  3. 关于Java中String类的intern()方法
  4. Hadoop 1.2.1 集群安装一
  5. 一些在线的WebEdit编辑器
  6. SpringBoot+Junt+Mock测试方法
  7. JSON的使用场景及注意事项介绍
  8. SpringMVC 实现注册登录
  9. static_const和reinterpret_cast
  10. python编辑代码的页面_使用CodeMirror实现Python3在线编辑器的示例代码