在 Eclipse 中编译 GriefPrevention 时遇到空分析问题。例如,PlayerEventHandler.java 中的第 304 行调用
Player#getLocation()
。此类的 API 规范可以在here找到。
问题在于该类继承自 Entity 和 OfflinePlayer 接口,它们的注释存在冲突。
对于实体,
getLocation()
定义为 NonNull
:
@NotNull
Location getLocation();
但是对于 OfflinePlayer 来说,它被定义为
Nullable
:
/**
* Gets the player's current location.
*
* @return the player's location, {@code null} if player hasn't ever played
* before.
*/
@Nullable
public Location getLocation();
我认为,鉴于这种情况,应优先考虑最不许可的注释(Nullable)。然而,IntelliJ 并不同意。这会产生一个问题,因为我无法在不禁用空注释的情况下使用 Eclipse 编译此代码,这是不可取的,并且使用 IntelliJ 的开发人员坚持认为这不是问题(根据他的 IDE)。
IntelliJ 或 Eclipse 的解释是否“更正确”,或者考虑到 API 规范中存在冲突的注释,结果是否不明确?
在测试这种不明确的继承时,IntelliJ 允许
@NotNull
没有任何警告或错误,但 @Nullable
会抛出警告:
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
public class Main {
interface ITestNotNull {
@NotNull
Object ambiguous();
}
interface ITestNullable {
@Nullable
Object ambiguous();
}
static class ITest implements ITestNullable, ITestNotNull {
@Override
// Method annotated with @Nullable must not override @NotNull method
public @Nullable Object ambiguous() {
return new Object();
}
}
public static void main(String[] args) {
ITest a = new ITest();
System.out.println(a.ambiguous());
}
}
在 Eclipse 中情况恰恰相反,但我收到了编译器错误:
import org.eclipse.jdt.annotation.NonNull;
import org.eclipse.jdt.annotation.Nullable;
public class Main {
interface ITestNotNull {
@NonNull
Object ambiguous();
}
interface ITestNullable {
@Nullable
Object ambiguous();
}
static class ITest implements ITestNullable, ITestNotNull {
@Override
// The return type is incompatible with '@NonNull Object' returned from
// Main.ITestNotNull.ambiguous() (mismatching null constraints)
public @Nullable Object ambiguous() {
return new Object();
}
}
public static void main(String[] args) {
ITest a = new ITest();
System.out.println(a.ambiguous());
}
}