什么是“覆盖等效"?它与@Override 有什么关系? [英] What is "override-equivalence" and how is it related to @Override?
问题描述
阅读 Javadoc 以了解 @Override
注释,我遇到了以下规则:
Reading the Javadoc for the @Override
annotation, I came across the following rule:
如果一个方法被这个注解需要注解类型编译器来生成错误消息除非至少满足以下条件之一:
If a method is annotated with this annotation type compilers are required to generate an error message unless at least one of the following conditions hold:
- 该方法确实覆盖或实现了在超类型中声明的方法.
- 该方法有一个签名,该签名与任何公共方法的签名等效在 Object 中声明.
第一点我很清楚,但我不确定第二点.
I'm clear on the first point, but I'm unsure about the second one.
覆盖等效"是什么意思?Object
的公共方法在这方面有何特殊之处?为什么这不在第一个标准中?
What does it mean by "override-equivalent"? How are public methods of Object
special in this respect? And why is this not covered under the first criterion?
更新说明:这仅适用于 Java 7 文档.Java 6 doc 没有说明任何关于覆盖等效的内容.为什么要改变?
Update note: This is only true of the Java 7 documentation. The Java 6 doc doesn't say anything about override-equivalence. Why the change?
在咨询 JLS 之后(第 8.4.2 节),我发现了覆盖等效的以下解释:
After consulting the JLS (Section 8.4.2), I found the following explanation of override-equivalence:
方法m1
的签名是m2
方法签名的子签名,如果要么:
The signature of a method
m1
is a subsignature of the signature of a methodm2
if either:
m2
与m1
具有相同的签名,或者m1
的签名与擦除相同(§4.6).
m2
has the same signature asm1
, or- the signature of
m1
is the same as the erasure (§4.6) of the signature ofm2
.
两个方法签名 m1
和 m2
是 override-equivalent 如果 m1
是一个m2
或 m2
的子签名是 m1
的子签名.
Two method signatures m1
and m2
are override-equivalent iff either m1
is a
subsignature of m2
or m2
is a subsignature of m1
.
据我所知,这回答了第一个问题(这是什么意思?")和第三个问题(为什么第一个条件不包括这个?").
As far as I can tell, this answers the first question ("What does it mean?") and the third question ("Why doesn't the first condition cover this?").
如果我理解正确(如果我不理解,请告诉我!),只有一种情况下两种方法是覆盖等效的,并且不属于第一个条件原始问题.当子类方法的签名的擦除与超类方法的签名相同时就是这种情况,反之则不然.
If I understand correctly (please inform me if I don't!), there is only one case where two methods are override-equivalent and which doesn't fall under the first condition of the original question. This is the case when the erasure of the signature of the subclass method is the same as the signature of the superclass method, but not the other way around.
那么,原始问题的第二个条件只有在我们尝试覆盖"Object
类的公共方法时尝试添加类型参数时才会起作用.我尝试了以下简单示例来测试这一点,并使用未使用的类型参数:
The second condition of the original question, then, would only come into play when we attempt to add type parameters when attempting to "override" a public method of the Object
class. I tried the following simple example to test this, with an unused type parameter:
public class Foo {
@Override
public <T> boolean equals(Object obj) {
return true;
}
}
当然,这个类不会编译,因为该方法实际上并没有覆盖equals
方法,因此与它发生冲突.但我仍然收到使用 @Override
注释的错误.假设这是 @Override
用法的第二个条件的有效示例,我错了吗?还是编译器生成了这个错误尽管不需要?
Of course, this class doesn't compile, because the method doesn't actually override the equals
method and thus clashes with it. But I also still receive an error for using the @Override
annotation. Am I wrong in assuming that this is a valid example of the second condition for @Override
usage? Or is the compiler generating this error despite not being required to?
推荐答案
这样做的原因是为了让您可以在接口中使用 @Override
批注,而不是从 Object 继承
但从 Object
隐式声明所有公共方法(参见 JLS 部分 9.2 接口成员).因此,您可以声明如下接口:
The reason for this is to allow you to use the @Override
annotation in interfaces, which do not inherit from Object
but implicitly declare all public methods from Object
(see JLS section 9.2 interface members). You are thus allowed to declare an interface like:
interface Bar { @Override int hashCode(); }
但是,您不能声明以下接口:
However, you would not be allowed to declare the following interface:
interface Quux { @Override Object clone(); }
因为 clone()
方法没有在接口中隐式声明(它不是 public
).
since the clone()
method is not implicitly declared in an interface (it is not public
).
这在 中有描述JLS 部分 9.6.3.4 @Override(@Override
的 Javadoc 仍然引用旧的部分编号)
This is described in JLS section 9.6.3.4 @Override (the Javadoc for @Override
still refers to an old section number)
这篇关于什么是“覆盖等效"?它与@Override 有什么关系?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!