Java公共枚举方法的目的
所以我有我的枚举
public enum Sample {
ValueA{
@Override
public String getValue(){ return "A"; }
},
ValueB{
@Override
public String getValue(){ return "B"; }
public void doSomething(){ }
};
abstract public String getValue();
};
,还有一些其他代码尝试使用该枚举。
Sample.ValueB.doSomething();
这看起来应该是有效的,但会产生错误“方法 doSomething() 对于类型 Sample 来说是未定义的”。相反,
Sample value = Sample.ValueB;
value.doSomething();
它产生相同的错误并且看起来合理。
我认为对于为什么第一个不起作用有一个合理的答案,并且它与两个示例在幕后是等效的有关。我希望有人能指出我为什么会这样的文档。
So I have my enum
public enum Sample {
ValueA{
@Override
public String getValue(){ return "A"; }
},
ValueB{
@Override
public String getValue(){ return "B"; }
public void doSomething(){ }
};
abstract public String getValue();
};
and I have some other code trying to use the enum.
Sample.ValueB.doSomething();
Which seems like it should be valid, but produces the error "The method doSomething() is undefined for the type Sample". As opposed to
Sample value = Sample.ValueB;
value.doSomething();
which produces the same error and seems reasonable.
I assume there is a reasonable answer as to why the first one doesn't work and it relates to the two examples being equivalent under the hood. I was hoping someone could point me towards the documentation on why it is that way.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
“字段”
ValueA
的类型是Sample
。这意味着您只能调用Sample
提供的ValueA
上的方法。来自 JLS §8.9.1 。枚举常量:更重要的是:从设计角度来看,
enum
值应该是统一的:如果某个操作可以使用一个特定值进行,那么它应该可以使用所有值进行(尽管这可能会导致执行不同的代码)。The type of the "field"
ValueA
isSample
. That means that you can only invoke methods onValueA
thatSample
provides. From JLS §8.9.1. Enum Constants:More importantly: From a design perspective
enum
values should be uniform: if some operation is possible with one specific value, then it should be possible with all values (although it might result in different code being executed).基本上,
Sample.ValueB
的编译时类型仍然是 Sample,尽管该值的执行时类型将是值B。因此,您的两个代码片段是等效的 - 客户端看不到仅存在于您的枚举值的一些中的“额外”方法。
您可以有效地将枚举视为声明如下字段:
Basically the compile-time type of
Sample.ValueB
is still Sample, even though the execution-time type of the value will beValueB
. So your two snippets of code are equivalent - clients don't get to see the "extra" methods which are only present in some of your enum values.You can effectively think of the enum as declaring a field like this:
当您编写时,
您并不是在创建
Sample
枚举的实例,而是创建enum Sample
的匿名子类的实例。这就是为什么doSomething()
方法未定义。更新:这可以证明如下:
尝试
打印
Sample$2
这意味着即使您在
Sample$2< 的实例中有方法
doSomething()
/code> 您已命名为ValueB
,您通过Sample
类型的超类引用来引用它,因此只有在类Sample< 中定义的那些方法/code> 将在编译时可见。
不过,您可以在运行时通过反射调用
doSomething()
。When you write
you are not creating an instance of the
Sample
enum, rather an instance of an anonymous sub-class of theenum Sample
. Thet's why the methoddoSomething()
is undefined.Update: this can be proved as follows:
Try this
prints
Sample$2
Which means that even though you have the method
doSomething()
in the instance ofSample$2
which you have namedValueB
, you are referring it through the super-class reference of typeSample
and hence only those methods defined in the classSample
will be visible at compile time.You can call that
doSomething()
at runtime via reflection though.public void doSomething(){ }
与private void doSomething(){ }
具有相同的效果。doSomething()
在 ValueB 外部不可见,除非您将doSomething()
添加到Sample
。每个
Sample
值都具有Sample
类型,因此对于不同的值(从外部角度来看),它不能具有不同的方法集。public void doSomething(){ }
will have same effect asprivate void doSomething(){ }
.doSomething()
is not visible outside ValueB unless you adddoSomething()
to theSample
.Each
Sample
value has typeSample
, so it cannot have different set of methods for different values (from outside perspective).