JAVA 深入理解 枚举类型 多路分发
枚举分析
Values 方法是编译器自动添加的 而不是父类继承的
package 枚举分析;
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){
System.out.println("--------------Analyzing "+enumClass+"----------------");
System.out.println("Interfaces: ");
for(Type t: enumClass.getGenericInterfaces()){
System.out.print(t);
}
System.out.println("Base :"+ enumClass.getAnnotatedSuperclass());
System.out.println("Methods: ");
Set<String> methods =new TreeSet<>();
for(Method m: enumClass.getMethods()){
methods.add(m.getName());
}
System.out.println(methods);
return methods;
}
public static void main(String [] argv){
Set<String> ExploreMethods = analyze(Explore.class);
//[compareTo, equals, getClass, getDeclaringClass, hashCode, name, notify, notifyAll, ordinal, toString, valueOf, values, wait]
Set<String> enumExploreMethods = analyze(Enum.class);
//[compareTo, equals, getClass, getDeclaringClass, hashCode, name, notify, notifyAll, ordinal, toString, valueOf, wait]
ExploreMethods.containsAll(enumExploreMethods);
}
}
getEnumConstants() 父类方法 获得所有枚举类型
enum Search{HITHER,YON};
public class UpcastNume {
public static void main(String [] argv){
Search[] vals = Search.values();//Values 方法是编译自动添加的 而不是从父类继承的
System.out.println(Arrays.deepToString(vals));
Enum e = Search.HITHER;
for(Enum en: e.getClass().getEnumConstants()){ //父类获得类型的方法
System.out.println(en + ", ");
}
System.out.println("================================");
Class<Integer> intClass = Integer.class;
try{
for(Object en: intClass.getEnumConstants()){//父类方法定义在Class类中,注意使用方法
System.out.println(en);
}
}catch (Exception ex){
System.out.println(ex.toString());
}
}
}
枚举覆盖父类方法
package 枚举分析;
public enum OverrideConstantSpecific {
NUT,
BOLT,
WHAHER{
void f(){
System.out.println("Overridden method");//覆盖
}
};
void f(){
System.out.println("default behavior");
}
public static void main(String [] argv){
for(OverrideConstantSpecific ocs: values()){
System.out.print(ocs + ": ");
ocs.f();
}
}
}
----->>>
NUT: default behavior
BOLT: default behavior
WHAHER: Overridden method
抽象方法
package 枚举分析;
import java.text.DateFormat;
import java.util.Date;
public enum ConstantSpecificMethod {
DATA_TIME{
@Override
String getInfo() {
return DateFormat.getDateInstance().format(new Date());
}
},
ClASSPAHT{
@Override
String getInfo() {
return "CLASSPATH";
}
},
VERSION{
@Override
String getInfo() {
return System.clearProperty("java.version");
}
};
abstract String getInfo();
public static void main(String [] argv){
for(ConstantSpecificMethod csm: values()){
System.out.println(csm.getInfo());
}
}
}
基础知识综合小例子
洗车
package 枚举分析;
import java.util.EnumSet;
public class CarWash {
public enum Cycle{
UNDERBODY{
@Override
void action() {
System.out.println("Spraying the underbody");
}
},
WHEELWACH{
@Override
void action() {
System.out.println("Washing the wheels");
}
},
PREWASH{
@Override
void action() {
System.out.println("Loosening the dirt");
}
},
BASIC{
@Override
void action() {
System.out.println("The basic wash");
}
},
HOTWAX{
@Override
void action() {
System.out.println("Applying hot wax");
}
},
RINSE{
@Override
void action() {
System.out.println("Rinsing");
}
},
BLOWDRY{
@Override
void action() {
System.out.println("Blowing dry");
}
};
abstract void action();
}
EnumSet<Cycle> cycles = EnumSet.of(Cycle.BASIC, Cycle.RINSE);
public void add(Cycle cycle){
cycles.add(cycle);
}
public void washCar(){
for(Cycle c: cycles){
c.action();
}
}
@Override
public String toString() {
return cycles.toString();
}
public static void main(String [] argv){
CarWash wash = new CarWash();
System.out.println(wash);
wash.washCar();
//Order of addition is unimportant:
wash.add(Cycle.BLOWDRY);
wash.add(Cycle.RINSE);
wash.add(Cycle.HOTWAX);
wash.add(Cycle.BLOWDRY);
wash.add(Cycle.BLOWDRY);
System.out.println(wash);
wash.washCar();
}
}
来点高端的 枚举多路并发
猜拳例子
//自限定
public interface Competitor <T extends Competitor<T>>{
OutCome compete(T competitor);
}
public class Enums {
private static Random rand = new Random(40);
public static <T extends Enum<T> & Competitor<T>> T random(Class<T> resbClass) {
T[] es = resbClass.getEnumConstants();
return es[rand.nextInt(es.length)];
}
}
public enum OutCome {
WIN{ public String toString() { return "胜";} },
LOSE { public String toString() { return "败"; } },
DRAW { public String toString() { return "平"; } };
public abstract String toString();
public String OutComeInfo(){
return "游戏结果";
}
}
public class RoShamBo {
public static <T extends Competitor<T>> void match(T a, T b){
System.out.println(a + " vs. " + b +": " + a.compete(b));
}
public static <T extends Enum<T> & Competitor<T>> void play(Class<T> resbClass, int size){
for(int i = 0; i< size; i++){
match(Enums.random(resbClass), Enums.random(resbClass));
}
}
}
最菜的实现的方式
import static 猜拳游戏.OutCome.DRAW;
import static 猜拳游戏.OutCome.LOSE;
import static 猜拳游戏.OutCome.WIN;
//通过函数重载实现分发
interface Item{
OutCome compete(Item it);
OutCome eval(Paper p);
OutCome eval(Scissors s);
OutCome eval(Rock r);
}
class Paper implements Item{
@Override
public OutCome compete(Item it) {
return it.eval(this);
}
@Override
public OutCome eval(Paper p) {
return DRAW;
}
@Override
public OutCome eval(Scissors s) {
return WIN;
}
@Override
public OutCome eval(Rock r) {
return LOSE;
}
@Override
public String toString() {
return "Paper";
}
}
class Scissors implements Item{
@Override
public OutCome compete(Item it) {
return it.eval(this);
}
@Override
public OutCome eval(Paper p) {
return LOSE;
}
@Override
public OutCome eval(Scissors s) {
return DRAW;
}
@Override
public OutCome eval(Rock r) {
return WIN;
}
@Override
public String toString() {
return "Scissors";
}
}
class Rock implements Item{
@Override
public OutCome compete(Item it) {
return it.eval(this);
}
@Override
public OutCome eval(Paper p) {
return WIN;
}
@Override
public OutCome eval(Scissors s) {
return LOSE;
}
@Override
public OutCome eval(Rock r) {
return DRAW;
}
@Override
public String toString() {
return "Rock";
}
}
public class RoshamBo1 {
static final int SIZE = 20;
private static Random rand = new Random(40);
public static Item newItem(){
switch (rand.nextInt(3)){
default:return null;
case 0:return new Scissors();
case 1:return new Paper();
case 2:return new Rock();
}
}
public static void match(Item a, Item b){
System.out.println(a + "VS. "+ b+ ": "+ a.compete(b));
}
public static void main(String [] argv) {
for (int i=0; i < SIZE; i++) {
match(newItem(), newItem());
}
}
}
结果和代码绑定
package 猜拳游戏;
import static 猜拳游戏.OutCome.*;
public enum RoshamBo2 implements Competitor<RoshamBo2> {
PAPER(DRAW, LOSE, WIN){
@Override
public String toString() {
return "布 ";
}
},
SCISSORS(WIN, DRAW, LOSE) {
@Override
public String toString() {
return "剪刀";
}
},
ROCK(LOSE, WIN, DRAW) {
@Override
public String toString() {
return "石头";
}
};
public abstract String toString();
private OutCome vPAPER, vSICISSOR, vROCK;
RoshamBo2(OutCome paper, OutCome scissors, OutCome rcok){
this.vPAPER = paper;
this.vSICISSOR = scissors;
this.vROCK = rcok;
}
@Override
public OutCome compete(RoshamBo2 it) {
switch (it){
default: return null;
case PAPER:return vPAPER;
case SCISSORS:return vSICISSOR;
case ROCK:return vROCK;
}
}
public static void main(String [] argv){
RoShamBo.play(RoshamBo2.class, 20);
}
}
枚举与switch 结合
package 猜拳游戏;
import static 猜拳游戏.OutCome.*;
public enum RoShamBo3 implements Competitor<RoShamBo3> {
PAPER{
public OutCome compete(RoShamBo3 it){
switch (it){
default:
case PAPER: return DRAW;
case SCISSORS:return LOSE;
case ROCK: return WIN;
}
}
},
SCISSORS{
public OutCome compete(RoShamBo3 it){
switch (it){
default:
case PAPER: return WIN;
case SCISSORS:return DRAW;
case ROCK: return LOSE;
}
}
},
ROCK{
public OutCome compete(RoShamBo3 it){
switch (it){
default:
case PAPER: return LOSE;
case SCISSORS:return WIN;
case ROCK: return DRAW;
}
}
};
@Override
public abstract OutCome compete(RoShamBo3 competitor);
public static void main(String [] argv){
RoShamBo.play(RoShamBo3.class, 20);
}
}
这个方法感觉比较优秀
package 猜拳游戏;
public enum RoShamBo4 implements Competitor<RoShamBo4> {
PAPER{
public OutCome compete(RoShamBo4 it){
return compete(ROCK, it);
}
},
SCISSORS{
public OutCome compete(RoShamBo4 it){
return compete(PAPER, it);
}
},
ROCK{
public OutCome compete(RoShamBo4 it) {
return compete(SCISSORS, it);
}
};
public OutCome compete(RoShamBo4 loser, RoShamBo4 opponent) {
return ((opponent == this)? OutCome.DRAW:((opponent == loser)? OutCome.WIN:OutCome.LOSE));
}
@Override
public OutCome compete(RoShamBo4 competitor){
return null;
}
public static void main(String [] argv){
RoShamBo.play(RoShamBo4.class, 20);
}
}
使用EnumMap
package 猜拳游戏;
import java.util.EnumMap;
import static 猜拳游戏.OutCome.*;
public enum RoShamBo5 implements Competitor<RoShamBo5> {
PARER, SCISSORS, ROCK;
static EnumMap<RoShamBo5, EnumMap<RoShamBo5, OutCome>> table = new EnumMap<RoShamBo5, EnumMap<RoShamBo5, OutCome>>(RoShamBo5.class);
static {
for (RoShamBo5 it: RoShamBo5.values()){
table.put(it, new EnumMap<RoShamBo5, OutCome>(RoShamBo5.class));
}
initRow(PARER, DRAW, LOSE, WIN);
initRow(SCISSORS, WIN, DRAW, LOSE);
initRow(ROCK, LOSE, WIN, DRAW);
}
private static void initRow(RoShamBo5 it, OutCome vPARER, OutCome vSCISSORS, OutCome vROCK) {
EnumMap<RoShamBo5, OutCome> row = RoShamBo5.table.get(it);
row.put(RoShamBo5.PARER, vPARER);
row.put(RoShamBo5.SCISSORS, vPARER);
row.put(RoShamBo5.ROCK, vROCK);
}
@Override
public OutCome compete(RoShamBo5 competitor) {
return table.get(this).get(competitor);
}
public static void main(String [] argv){
RoShamBo.play(RoShamBo5.class, 20);
}
}
结合数组 (很高效)
package 猜拳游戏;
import static 猜拳游戏.OutCome.*;
public enum RoShamBo6 implements Competitor<RoShamBo6> {
PARER, SCISSORS, ROCK;
private static OutCome[][] table = {
{DRAW, LOSE, WIN},
{WIN, DRAW, LOSE},
{LOSE, WIN, DRAW}
};
@Override
public OutCome compete(RoShamBo6 competitor) {
return table[this.ordinal()][competitor.ordinal()];
}
public static void main(String [] argv){
RoShamBo.play(RoShamBo6.class, 20);
}
}