【问题标题】:Eclipse external null annotation for java.lang.Object#getClass()java.lang.Object#getClass() 的 Eclipse 外部空注释
【发布时间】:2015-09-16 20:03:24
【问题描述】:

我正在使用 Eclipse Mars 中提供的外部空注释工具。我正在尝试为java.lang.Object#getClass() 添加外部注释,但似乎无法正确签名。我尝试了以下变体:

@NonNull Class<?> getClass() [()L1java/lang/Class<*>;]
@NonNull Class<@NonNull ?> getClass() [()L1java/lang/Class<*1>;]

但在将调用getClass() 的结果传递给接受Class&lt;?&gt; 实例的方法时仍会收到警告,其中该参数使用@NonNull 进行注释。

以下是重现该问题的最小 Eclipse Mars 项目的相关文件(此示例使用上面的第一个空注释变体,但在使用第二个变体时我也收到相同的警告):

适用于 64 位 Windows 的 Eclipse Mars 版本(4.5.0;20150621-1200)
Oracle JDK 1.8.0_60

src/bar/Foo.java

package bar;

public class Foo {
    private static void printType(Class<?> type) {
        System.out.println(type.getName());
    }

    public static void main(String[] args) {
        Foo foo = new Foo();
        printType(foo.getClass());
    }
}

src/bar/package-info.java

@org.eclipse.jdt.annotation.NonNullByDefault
package bar;

annotations/java/lang/Object.eea

class java/lang/Object
getClass
 ()Ljava/lang/Class<*>;
 ()L1java/lang/Class<*>;

.settings/org.eclipse.jdt.core.prefs(部分)

eclipse.preferences.version=1
org.eclipse.jdt.core.compiler.annotation.inheritNullAnnotations=enabled
org.eclipse.jdt.core.compiler.annotation.missingNonNullByDefaultAnnotation=warning
org.eclipse.jdt.core.compiler.annotation.nonnull=org.eclipse.jdt.annotation.NonNull
org.eclipse.jdt.core.compiler.annotation.nonnullbydefault=org.eclipse.jdt.annotation.NonNullByDefault
org.eclipse.jdt.core.compiler.annotation.nullable=org.eclipse.jdt.annotation.Nullable
org.eclipse.jdt.core.compiler.annotation.nullanalysis=enabled
...
org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.8
...
org.eclipse.jdt.core.compiler.compliance=1.8
...
org.eclipse.jdt.core.compiler.problem.includeNullInfoFromAsserts=enabled
...
org.eclipse.jdt.core.compiler.problem.nonnullParameterAnnotationDropped=warning
org.eclipse.jdt.core.compiler.problem.nullAnnotationInferenceConflict=error
org.eclipse.jdt.core.compiler.problem.nullReference=error
org.eclipse.jdt.core.compiler.problem.nullSpecViolation=error
org.eclipse.jdt.core.compiler.problem.nullUncheckedConversion=warning
...
org.eclipse.jdt.core.compiler.problem.potentialNullReference=error
...
org.eclipse.jdt.core.compiler.problem.redundantNullAnnotation=warning
org.eclipse.jdt.core.compiler.problem.redundantNullCheck=warning
...
org.eclipse.jdt.core.compiler.problem.syntacticNullAnalysisForFields=enabled
...
org.eclipse.jdt.core.compiler.source=1.8

.classpath

<?xml version="1.0" encoding="UTF-8"?>
<classpath>
    <classpathentry kind="src" path="src"/>
    <classpathentry kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER/org.eclipse.jdt.internal.debug.ui.launcher.StandardVMType/JavaSE-1.8">
        <attributes>
            <attribute name="annotationpath" value="/null-annotation-test/annotations"/>
        </attributes>
    </classpathentry>
    <classpathentry kind="lib" path="org.eclipse.jdt.annotation_2.0.100.v20150311-1658.jar"/>
    <classpathentry kind="output" path="bin"/>
</classpath>

对于上述项目,我在 Foo.java 的第 10 行(其中调用了 printType)收到以下警告:

Null type safety (type annotations): The expression of type 'Class<capture#of ? extends Foo>' needs unchecked conversion to conform to '@NonNull Class<?>'

这与我在没有外部空注释存在的情况下得到的警告相同。

如何为java.lang.Object#getClass() 正确创建外部空注释以消除此警告?还是我在printType的声明中有问题?

【问题讨论】:

  • 我不确定这是否可行。 getClass 是一个非常神奇的功能;它在编译器的类型检查器中被特殊处理。

标签: java eclipse null annotations external-annotations


【解决方案1】:

Louis Wasserman 是正确的,就类型检查而言,没有一个 getClass() 方法,但每个类都有自己的方法和专门的签名。因此,.eea 文件中的任何签名都不会匹配实际的 getClass() 方法。

我提交了一个RFE 以将更多关于getClass() 的特殊知识放入编译器中,这样这只野兽就不需要外部注释了。

编辑:此功能已实现并将随 Eclipse 4.6 (Neon) 一起发布。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-11-15
    • 2016-11-22
    • 2012-09-17
    • 1970-01-01
    相关资源
    最近更新 更多