我如何要求通用参数是实现接口的枚举?

发布于 2024-07-26 18:47:37 字数 1070 浏览 3 评论 0 原文

我并不是 100% 相信这是一个好主意,但我今天遇到了一些代码,目前的实现如下:

class MyWidget <T extends Enum<T> > {
  MyWidget(Map<T, Integer> valueMap) {
    mValueMap = valueMap;
  }

  Map<T, Integer> mValueMap;
}

其中 MyWidget then 提供了使用 mValueMap 进行转换的方法传入的 EnumInteger 之间的传入。

我正在考虑做的是尝试重构它,以便我声明我的枚举:

interface MyInterface {
  public Integer getValue();
}

enum MyEnum implements MyInterface {
  foo, bar;
  public Integer getValue() {
    return ordinal();
  }
}

然后我就能够将 MyWidget 重写为看起来模糊的东西:

public class MyWidget<T extends Enum<T> extends MyInterface> {
  ...
}

然后就能够从 MyInterfaceMyWidget 内的 T 类型对象调用 getValue() 方法。 当然,问题在于“ extends MyInterface>”不是有效的语法。 有什么办法可以解决这个问题吗?

我不想只拥有 MyWidget,因为 T 是一个枚举也很重要。

提前致谢!

I'm not 100% convinced that this is a good idea, but I bumped into some code today that's currently implemented as:

class MyWidget <T extends Enum<T> > {
  MyWidget(Map<T, Integer> valueMap) {
    mValueMap = valueMap;
  }

  Map<T, Integer> mValueMap;
}

where MyWidget then offers methods that use mValueMap to convert the passed-in Enum to/from an Integer.

What I was considering doing was trying to refactor this, so that I'd declare my enumeration:

interface MyInterface {
  public Integer getValue();
}

enum MyEnum implements MyInterface {
  foo, bar;
  public Integer getValue() {
    return ordinal();
  }
}

And I'd then be able to rewrite MyWidget into something that looked vaguely like this:

public class MyWidget<T extends Enum<T> extends MyInterface> {
  ...
}

and would then be able to call the getValue() method from MyInterface on T-type objects within MyWidget. The problem, of course, is that "<T extends Enum<T> extends MyInterface>" isn't valid syntax. Is there any way to pull this off?

I don't want to just have MyWidget<T extends MyInterface>, because it's also important that T be an enumeration.

Thanks in advance!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

别想她 2024-08-02 18:47:37

使用“&”代替:

public class MyWidget<T extends Enum<T> & MyInterface> {
    ...
}

JLS 将此称为“交叉类型”,但我在 Java 教程中找不到任何提及。 我只想说它完全符合您希望“extends”所做的事情。

另外,我应该提到的是,您可以在交叉类型中拥有任意多种类型。 因此,如果您愿意,您可以这样做:

public class MyWidget<T extends Enum<T> & MyInterface & Serializable & Cloneable> {
    ...
}

[注意:此代码示例不应被解释为对 Cloneable 接口的认可; 当时只是方便而已。]

Use an '&' instead:

public class MyWidget<T extends Enum<T> & MyInterface> {
    ...
}

The JLS calls this an "intersection type", but I can find no mention of it in the Java tutorials. I'll just say that it does exactly what you were wishing that "extends" would do.

Also, I should mention that you can have as many types as you want in the intersection type. So if you wanted, you could do:

public class MyWidget<T extends Enum<T> & MyInterface & Serializable & Cloneable> {
    ...
}

[Note: this code sample should not be construed as an endorsement of the Cloneable interface; it was merely handy at the time.]

李白 2024-08-02 18:47:37

JDK 7 的 JSR 203(新的新 IO)内容大量使用实现接口的枚举(例如:http://openjdk.java.net/projects/nio/javadoc/java/nio/file/FileVisitOption.html) 允许它们进行一些摆动将来有空间用于未来额外的枚举选项集。 因此,这是一种可行的方法,并且显然是在一个大型 Sun 项目中经过深思熟虑后选择的方法。

The JSR 203 (new new IO) stuff for JDK 7 is making a lot of use of enums that implement interfaces (for example: http://openjdk.java.net/projects/nio/javadoc/java/nio/file/FileVisitOption.html) to allow them some wiggle room in the future for future additional sets of enum options. So that is a feasible approach and obviously one that was chosen after a lot of thought in one large Sun project.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文