Java Enum方法

时间:2013-09-18 22:55:17

标签: java enums enumeration

我想声明一个枚举方向,它有一个返回相反方向的方法(以下语法不正确,即枚举无法实例化,但它说明了我的观点)。这在Java中是否可行?

以下是代码:

public enum Direction {

     NORTH(1),
     SOUTH(-1),
     EAST(-2),
     WEST(2);

     Direction(int code){
          this.code=code;
     }
     protected int code;
     public int getCode() {
           return this.code;
     }
     static Direction getOppositeDirection(Direction d){
           return new Direction(d.getCode() * -1);
     }
}

6 个答案:

答案 0 :(得分:187)

对于那些通过标题引诱的人:是的,你可以在枚举中定义自己的方法。如果您想知道如何调用这种非静态方法,那么您可以像使用任何其他非静态方法一样进行操作 - 您可以在定义或继承该方法的类型实例上调用它。在枚举的情况下,这样的实例只是ENUM_CONSTANT s。

所以你需要的只是EnumType.ENUM_CONSTANT.methodName(arguments)


现在让我们回答一下问题。其中一个解决方案可能是

public enum Direction {

    NORTH, SOUTH, EAST, WEST;

    private Direction opposite;

    static {
        NORTH.opposite = SOUTH;
        SOUTH.opposite = NORTH;
        EAST.opposite = WEST;
        WEST.opposite = EAST;
    }

    public Direction getOppositeDirection() {
        return opposite;
    }

}

现在Direction.NORTH.getOppositeDirection()将返回Direction.SOUTH


这里用更多的“hacky”方式来说明@jedwards comment,但它并不像第一种方法那样灵活

public enum Direction {
    NORTH, EAST, SOUTH, WEST;

    private static final Direction[] VALUES = values();//cached values 
                                                       //to avoid recreating array

    public Direction getOppositeDirection() {
        return VALUES[(ordinal() + 2) % 4];
    }
}

答案 1 :(得分:141)

对于像这样的小枚举,我发现最可读的解决方案是:

public enum Direction {

    NORTH {
        @Override
        public Direction getOppositeDirection() {
            return SOUTH;
        }
    }, 
    SOUTH {
        @Override
        public Direction getOppositeDirection() {
            return NORTH;
        }
    },
    EAST {
        @Override
        public Direction getOppositeDirection() {
            return WEST;
        }
    },
    WEST {
        @Override
        public Direction getOppositeDirection() {
            return EAST;
        }
    };


    public abstract Direction getOppositeDirection();

}

答案 2 :(得分:22)

这有效:

public enum Direction {
    NORTH, SOUTH, EAST, WEST;

    public Direction oppose() {
        switch(this) {
            case NORTH: return SOUTH;
            case SOUTH: return NORTH;
            case EAST:  return WEST;
            case WEST:  return EAST;
        }
        throw new RuntimeException("Case not implemented");
    }
}

答案 3 :(得分:14)

创建一个抽象方法,并让每个枚举值覆盖它。由于您在创建时知道相反的情况,因此无需动态生成或创建它。

虽然不能很好地阅读;或许switch更易于管理?

public enum Direction {
    NORTH(1) {
        @Override
        public Direction getOppositeDirection() {
            return Direction.SOUTH;
        }
    },
    SOUTH(-1) {
        @Override
        public Direction getOppositeDirection() {
            return Direction.NORTH;
        }
    },
    EAST(-2) {
        @Override
        public Direction getOppositeDirection() {
            return Direction.WEST;
        }
    },
    WEST(2) {
        @Override
        public Direction getOppositeDirection() {
            return Direction.EAST;
        }
    };

    Direction(int code){
        this.code=code;
    }
    protected int code;

    public int getCode() {
        return this.code;
    }

    public abstract Direction getOppositeDirection();
}

答案 4 :(得分:5)

是的,我们一直这样做。您返回静态实例而不是新对象

 static Direction getOppositeDirection(Direction d){
       Direction result = null;
       if (d != null){
           int newCode = -d.getCode();
           for (Direction direction : Direction.values()){
               if (d.getCode() == newCode){
                   result = direction;
               }
           }
       }
       return result;
 }

答案 5 :(得分:0)

public enum Direction {
    NORTH, EAST, SOUTH, WEST;

    public Direction getOppositeDirection(){
        return Direction.values()[(this.ordinal() + 2) % 4];
    }
}

枚举有一个静态值方法,它返回一个数组,该数组按照声明的顺序包含枚举的所有值。 source

由于NORTH获得1,EAST获得2,SOUTH获得3,WEST获得4; 你可以创建一个简单的等式来得到相反的等式:

(值+ 2)%4