我在Eclipse IDE中发现了一些奇怪的东西。我们说我有以下课程:
public class Super {
@Deprecated
public void doNotUseThisMethod() {
// do magic
}
}
public class Sub extends Super{
@Override
public void doNotUseThisMethod() {
// why is this not deprecated?
}
}
当然,覆盖已弃用的方法会导致警告(因为不使用它的原因相同)。仍然在Eclipse Luna和Mars的全新工作区中,上面的代码根本不会产生警告。我无法找到任何方法来启用它。
我发现this bug用于接口(如果Super
是一个接口,我会得到它,应该没有警告),这意味着曾经有一次警告。
那发生了什么?是否有任何理由覆盖已弃用的方法不应导致警告?我可以再做一些事情来启用此功能吗?
答案 0 :(得分:5)
JLS在这一点上非常清楚(因为它在大多数情况下都是如此)。
注释@Deprecated的程序元素是程序员不鼓励使用的程序元素,通常是因为它很危险,或者因为存在更好的替代方案。
当在显式或隐式声明的构造中使用(通过名称覆盖,调用或引用)声明使用@Deprecated注释的类型,方法,字段或构造函数时,Java编译器必须生成弃用警告,除非:
使用是在一个本身注释的实体内 注释@Deprecated;或
使用是在注释的实体内使用注释@SuppressWarnings来抑制警告("弃用");或
使用和声明都在同一个最外层。
(https://docs.oracle.com/javase/specs/jls/se8/html/jls-9.html#jls-9.6.4.6)
为了完全符合JLS,Eclipse 必须标记您的doNotUseThisMethod()
并发出警告。很久以前它似乎曾经这样做过,但在2003年bug 48335出现了,警告变成了偏好。如错误评论中所述,默认值是"禁用"。 (默认值应为"已启用"甚至可以远程符合JLS。请随意提交错误以更改它。)我还没有进行详尽的搜索,但是因为你看到了与此一致的行为,我会走出困境并说这是从那以后它一直存在的。
由于它是首选项,您可以更改它。只需转到" Window - >首选项",然后选择" Java - >编译器 - >错误/警告&#34 ;.向下滚动到"弃用和限制的API"并选中"信号覆盖或实施弃用方法"旁边的框。右侧有一个下拉菜单,略高于您可以选择的位置"错误","警告"或"忽略"。选择你喜欢的那个。
该设置仅影响您的本地IDE。
要使整个团队使用该设置,您需要设置项目特定设置。在同一首选项屏幕上,右上角有一个指向"配置项目特定设置"的链接。单击它,选择要为其设置首选项的项目,并执行上述相同操作。这将创建一个名为" org.eclipse.jdt.core.prefs"的文件。在你的项目" .settings"夹。 (您无法在Package Explorer中看到它们。您需要在Navigator视图中查看它们。)创建后,您可以将它们添加到源代码管理中,它们将适用于所有人在您的团队中完成该项目。
是的,你必须为每个项目都这样做。
答案 1 :(得分:2)
实际上,这种行为对我来说是正确的:当你覆盖一个方法时,你会为它实现一个新的代码。
为避免错误,如果使用不推荐使用的超级方法,eclipse会发出警告:
class Sub extends Super{
@Override
public void doNotUseThisMethod() { // <---------------*
super.doNotUseThisMethod(); // deprecated! <----*
}
}
但是如果在不使用已弃用的super.method()
的情况下覆盖已弃用的方法functionallity,则根据定义不会弃用新方法,因为您在不使用旧方法的情况下实现了。
public class Sub extends Super{
@Override
public void doNotUseThisMethod() {
// new logic + not using super.method() = not a deprecated method!!
}
}
如果覆盖弃用的那个,不应该使用,也必须注释为不推荐使用,如下所示:
public class Super {
@Deprecated
public void doNotUseThisMethod() {
// do magic
}
}
public class Sub extends Super{
@Override
@Deprecated // <---------------------------*
public void doNotUseThisMethod() { // |
// this is deprecated also!!!! // <-----*
}
}
SIDENOTE :如果您的方法名称可能导致混淆,则会出现另一个问题。
但是没有@Deprecate也意味着&#34;我们很快就会删除这个方法&#34;,由于@Override注释,这将破坏子类的代码? (这正是我需要警告的原因 - 防止其他开发人员覆盖我要删除的方法。但是因为它们甚至不会得到警告。) - Steffi S.
实际上开发人员可能会删除该方法,但是弃用更多的是在某些方法中不使用代码,因为它已经过时,然后开发人员使用新名称创建一个新名称,并将其弃用为遗留名称。
但是......在删除此方法的情况下会发生什么?
首先,这将意味着更改Java(或框架或工具)版本,这应该谨慎进行,弃用的方法不会成为您唯一的问题。
如果您选择主要版本并删除了一些已弃用的方法,您将不会遇到太多问题......为什么?您的IDE将清楚地标记此方法并显示错误,您只需要删除@Override
注释,在您的覆盖方法中保持逻辑安全。
答案 2 :(得分:-3)
在类的开头需要@SuppressWarnings(“弃用”)来实现不推荐的接口/函数。