我有一个Java枚举,表示给定字段的潜在值,以及用于标识该值的唯一标识符:
public enum MyEnum {
TYPEA("A"),
TYPEB("B")
private String code;
private MyEnum(String code){
this.code = code;
}
public String getCode(){
return code;
}
}
我想添加一个自定义比较器:
public boolean equals(String code){
return getCode().equals(code);
}
这将允许我将我的枚举与字符串进行比较。
我有遗失的缺陷吗?我看不出任何明显的错误......
答案 0 :(得分:14)
嗯,有两件事:
MyEnum.A.equals("A")
为真,但"A".equals(MyEnum.A)
为假。我不会这样做 - 你希望用代码执行相等检查,这很容易做到......但是明确它是明确的。
毕竟,这只是:
之间的区别if (value.equals("A"))
和
if (value.getCode().equals("A"))
我认为后者更清楚。
答案 1 :(得分:6)
陷阱很简单:你没有覆盖equals(Object)
,你引入了另一种方法equals(String)
。 equals
的任何基础结构调用都不会对您的对象使用该方法,因为动态调度仅适用于调用该方法的对象的运行时类型以及所有 static 类型的运行时类型方法参数用于在编译时解析方法签名。
如果您将此“更正”为equals(Object)
,但保留逻辑,那么您违反了equals
合同,因为您不满足对称属性:如果将另一个字符串与您的对象进行比较通过String.equals(yourObject)
它将返回false,你不能影响它。这是使用Java的单调度机制来定义等式关系的限制。
值得庆幸的是,枚举功能已经阻止您通过对equals
和hashCode
进行硬编码并使其成为最终版本来尝试此操作。