一、枚举类定义
枚举类也是一个类,只不过它的实例是在创建类就确定下来的,需要在第一行声明该枚举类的所有实例
枚举类通常应该被设计成不可变类,即它的成员变量是private final 类型(如果成员变量也是引用则需写出一定保护的代码),构造器隐藏(使用private),在构造器中初始化成员变量,所以需要带参构造器,同时在第一行声明该枚举的所有实例时应该传入参数。
上述代码如下,定义一个Gender枚举类
非抽象的枚举类默认为final,即不能拥有子类。
public enum Gender { //第一行指定该枚举的对象,由于构造器带参数,所以创建对象的时候需要传入参数 //这种写法相当于如下写法: // public static final Gender MALE = new Gender("男"); // public static final Gender FEMALE = new Gender("女"); MALE("男"),FEMALE("女"); private final String name; private Gender(String name){ this.name = name; } public String getName() { return name; } }
当项目很大时,合理使用枚举类可以使代码更易读更健壮
二、实现接口的枚举类
接口:
public interface GenderDesc { void info(); }
与普通的类实现接口相同,必须实现接口中所有的抽象方法,如果由枚举类来实现这些抽象方法,则每个对象使用这些方法时都具有相同的行为方式。
public enum Gender implements GenderDesc{ //第一行指定该枚举的对象,由于构造器带参数,所以创建对象的时候需要传入参数 //这种写法相当于如下写法: // public static final Gender MALE = new Gender("男"); // public static final Gender FEMALE = new Gender("女"); MALE("男"),FEMALE("女"); private final String name; private Gender(String name){ this.name = name; } public String getName() { return name; } @Override public void info() { System.out.println("xing"); } }
如果想为不同的枚举对象应用不同的行为方式,需要隐式的将枚举类转化为抽象的枚举类,抽象枚举类可以拥有子类,先看代码
public enum Gender implements GenderDesc{ //第一行指定该枚举的对象,由于构造器带参数,所以创建对象的时候需要传入参数 //这种写法相当于如下写法: // public static final Gender MALE = new Gender("男"); // public static final Gender FEMALE = new Gender("女"); MALE("男"){ @Override public void info() { System.out.println("male"); } } ,FEMALE("女"){ @Override public void info() { System.out.println("female"); } }; private final String name; private Gender(String name){ this.name = name; } public String getName() { return name; } }
这样子的写法,在创建MALE和FEMALE实例时并不是直接创建实例,而是创建Gender枚举类的两个内部匿名子类,创建匿名内部类时会自动穿件该类的实例(前一节讲过),在子类中对接口的抽象方法重写。这样会将Gender类隐式转化为抽象类,可以使得MALE和FEMALE实例对同一方法有不同行为。
三、包含抽象方法的枚举类
与实现接口的抽象枚举类为每个实例衍生匿名子类相似,直接看代码
public enum Gender { //第一行指定该枚举的对象,由于构造器带参数,所以创建对象的时候需要传入参数 //这种写法相当于如下写法: // public static final Gender MALE = new Gender("男"); // public static final Gender FEMALE = new Gender("女"); MALE("男"){ @Override protected void goToWC() { System.out.println("站着"); } } ,FEMALE("女"){ @Override protected void goToWC() { System.out.println("坐着或蹲着"); } }; private final String name; private Gender(String name){ this.name = name; } public String getName() { return name; } protected abstract void goToWC(); }
写在最后:使用enum定义的枚举类默认继承了java.lang.Enum,而不是java.lang.Object,到这里,java面向对象的部分已经学习完毕,接下来该学习一些java的基础类库使用方法以及部分原理。