1、简单介绍
a)enum继承了Enum类,而java属于单继承,故enum不能再继承其他类,但可以实现接口。
b)枚举属于全局变量,不能实例化enum故,构造器为private类型。
定义一个枚举类型:
package com.qunar.flight.model;
/**
* Created by nostalie.zhang on 2016/12/21.
*/
public enum Color {
//重写Color的say方法,还可以定义其他方法,但不能直接调用。
RED(1.2){
public String getStr() {
return "红色的getValue方法";
}
@Override
public void say() {
System.out.println("红色的say方法");
}
},PINK(3.0){
@Override
public void say() {
System.out.println("粉色的say方法");
}
},GREEN(4.3){
@Override
public void say() {
System.out.println("绿色的say方法");
}
},BLUE(5.6){
@Override
public void say() {
System.out.println("蓝色的say方法");
}
};
//定义构造器传入double类型。
Color(Double value){
this.value=value;
}
private Double value;
public Double getValue() {
return value;
}
public void say(){
System.out.println("Color的say方法");
}
}
编写测试类:
package com.qunar.flight.model;
import junit.framework.TestCase;
import org.junit.Test;
import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.util.EnumMap;
import java.util.Iterator;
import java.util.Map;
public class ColorTest extends TestCase {
@Test
public void testColor() throws NoSuchMethodException, InvocationTargetException, IllegalAccessException {
Color red=Color.RED;
System.out.println("执行Color.RED的say方法:");
red.say();
//red.getStr();无法直接调用在red中声明的方法。
Method mothod = red.getClass().getMethod("getStr");
mothod.setAccessible(true);
String value=(String)mothod.invoke(red);
System.out.println("使用反射调用RED的getStr()方法,返回值为:"+value);
System.out.println("==========================================================================================");
Method [] methods=Color.RED.getClass().getDeclaredMethods();
System.out.println("在Color.RED中定义的方法:");
for(Method method : methods){
System.out.println(Modifier.toString(method.getModifiers())+" "+method.getReturnType().getName()+" "+method.getName()+" ("+method.getParameterTypes()+" )");
}
System.out.println("=============================================================================================");
Method [] methods1=Color.class.getDeclaredMethods();
System.out.println("在Color中定义的方法:");
for(Method method : methods1){
System.out.println(Modifier.toString(method.getModifiers())+" "+method.getReturnType().getName()+" "+method.getName()+" ("+method.getParameterTypes()+" )");
}
System.out.println(Color.RED.equals(Color.valueOf("RED")));
System.out.println(Color.PINK==Color.valueOf("PINK"));
System.out.println("执行Color的values方法:");
for(Color color:Color.values()){
System.out.print(color);
System.out.print(" ");
}
System.out.println("");
System.out.println("Color.GREEN的ordinal:"+Color.GREEN.ordinal());
System.out.println(Color.BLUE.getValue());
System.out.println("=============================================================================================");
System.out.println("Color.RED的超类是:"+Color.RED.getClass().getSuperclass().getName());
Constructor[] constructors=Color.class.getDeclaredConstructors();
for(Constructor con : constructors){
System.out.println("Color的构造方法:"+con);
}
Constructor[] constructors1=Color.BLUE.getClass().getDeclaredConstructors();
for(Constructor con : constructors1){
System.out.println("Color.BLUE的构造方法:"+con);
}
/**
* EnumMap的key的hash值不会出现重复,属于完美hash。(听人说的,有时间研究下,待考证...)
*/
EnumMap<Color,String> colorMap=new EnumMap<Color, String>(Color.class);
colorMap.put(Color.BLUE,"blue");
colorMap.put(Color.RED,"red");
for(Iterator<Map.Entry<Color,String>> iterator=colorMap.entrySet().iterator();iterator.hasNext();){
Map.Entry<Color,String> map=iterator.next();
System.out.println(map.getKey()+"---"+map.getValue());
}
}
}
运行结果:
执行Color.RED的say方法:
红色的say方法
使用反射调用RED的getStr()方法,返回值为:红色的getValue方法
==========================================================================================
在Color.RED中定义的方法:
public java.lang.String getStr ([Ljava.lang.Class;@28d72e3f )
public void say ([Ljava.lang.Class;@471d3f0b )
=============================================================================================
在Color中定义的方法:
public static [Lcom.qunar.flight.model.Color; values ([Ljava.lang.Class;@7f5d84e0 )
public static com.qunar.flight.model.Color valueOf ([Ljava.lang.Class;@54becf73 )
public java.lang.Double getValue ([Ljava.lang.Class;@3b25b27c )
public void say ([Ljava.lang.Class;@27e9093a )
true
true
执行Color的values方法:
RED PINK GREEN BLUE
Color.GREEN的ordinal:2
5.6
=============================================================================================
Color.RED的超类是:com.qunar.flight.model.Color
Color的构造方法:private com.qunar.flight.model.Color(java.lang.String,int,java.lang.Double)
Color的构造方法:com.qunar.flight.model.Color(java.lang.String,int,java.lang.Double,com.qunar.flight.model.Color$1)
Color.BLUE的构造方法:com.qunar.flight.model.Color$4(java.lang.String,int,java.lang.Double)
RED---red
BLUE---blue
Process finished with exit code 0
2、小结
对于程序员来说,文字的表述能力远不如代码来的直接,其实想说的都已经在代码里了。
来简单看一下运行结果,我们发现Color.RED,Color.PINK,Color.BLUE,Color.GREEN
本就是一个类,只不过编译器对他们进行了一些特殊处理。通过反射依旧可以拿到它们自己定义的方法。
再来说一下构造函数,看到Color有一个构造函数Color(String,int,Double)
,但是我们声明的构造函数是Color(Double)
,这里编译器做了一些处理,String
对应Enum
类中的name,int
对应Enum
类中的ordinal,String自动把你声明的枚举如BLUE对应成字符串传入(区分大小写),int对用声明的顺序,从0
开始,RED
处于0
位置,ordinal
为0
;
常用方法:
values()
返回枚举数组,用以遍历
valueof(String)
根据String
返回枚举类型(实际是维护了一个HashMap
,以name
作为key
,对应的枚举类作为value
)