Java:我可以在枚举类型中使用两个不同的名称来表示相同的事物吗?

10
我有一个枚举类,包含基本方向(North, East, South, West):
public enum Direction {
    NORTH,
    EAST,
    SOUTH,
    WEST;
}

有没有办法可以使用多个名称来表示同一件事情?例如像这样:

public enum Direction {
    NORTH or N,
    EAST or E,
    SOUTH or S,
    WEST or W;
}

实际上我想做的是给一个变量赋值为N或者NORTH并且这两个操作完全相同。

例子:

Direction direction1=new Direction.NORTH;
Direction direction2=new Direction.N;
//direction1==direction2
3个回答

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

  // Convenience names.
  public static final Direction N = NORTH;
  public static final Direction E = EAST;
  public static final Direction S = SOUTH;
  public static final Direction W = WEST;
}

使用缩写是合法的,但是采用自动生成的 valueOf 方法时,"N" 将无法正常工作。也就是说,Direction.valueOf("N") 将会抛出一个 IllegalArgumentException 而不是返回 Direction.NORTH

此外,在值为 Directionswitch 中,你也不能写 case N:。你必须使用全称。

除此之外,缩写形式应该可以和完整版本一样正常工作。你可以在 EnumSet 中使用 Direction.N,将其与 Direction.NORTH 进行比较,获取其 name()(即 "NORTH"),进行静态导入 import static yourpackage.Direction.N; 等操作。


5
你可以这样做(省略东西和西方)。
public enum Direction {
    NORTH {
        @Override
        Direction getDirection() {
            return NORTH;
        }
    },
    N {
        @Override
        Direction getDirection() {
            return NORTH;
        }
    },
    SOUTH {
        @Override
        Direction getDirection() {
            return SOUTH;
        }
    },
    S {
        @Override
        Direction getDirection() {
            return SOUTH;
        }
    }   ;

    abstract Direction getDirection();
}

那么你可以像这样做:

public void foo(Direction arg) {
  Direction d = arg.getDirection();
}

那么你将始终只涉及到北、南、东和西。

1
1+。还没有考虑过这个。 - Anthony Accioly
1
但是 N == NORTH 将返回 false。这意味着你必须始终记得使用 getDirection(),这很麻烦,使你的代码变得脆弱...而且可能比在添加 N 作为缩写之前更冗长。 - Stephen C
@Stephen 同意。这不是一个理想的解决方案,但只是“一个”解决方案。 - JustinKSU

0

嗯,也许可以使用“客户端枚举”来保存实际的“有意义的枚举”变量?

public enum Direction {
    NORTH(BaseDirection.NORTH),
    N(BaseDirection.NORTH),
    EAST(BaseDirection.EAST),
    E(BaseDirection.EAST),
    SOUTH(BaseDirection.SOUTH),
    S(BaseDirection.SOUTH),
    WEST(BaseDirection.WEST),
    W(BaseDirection.WEST);

    private BaseDirection baseDirection;

    private Direction(BaseDirection baseDirection) {
        this.baseDirection = baseDirection;
    }

    public BaseDirection getBaseDirection() {
        return baseDirection;
    }           
}

public enum BaseDirection {
    NORTH,
    EAST,
    SOUTH,
    WEST;
}

可能有点过度设计,但您可以将 Direction 暴露给客户端代码,并使用 getBaseDirection 进行实际逻辑。


如果你想让类似 N == NORTH 的语句成立,你需要做更多的工作。 - ChrisH
问题在于 N != NORTH。你需要使用 equals 比较方向值,而 switch(direction){...} 需要同时使用两种选择。这有点违背了使用枚举的目的。 - Stephen C

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接