如何摆脱 TreeMap 的 eclipse neon 中的 "Null type safety" 警告
How to get rid of "Null type safety" warning in eclipse neon for TreeMap
如何消除此示例代码中的警告。
我将 Eclipse Neon 与 Java 1.8 和 org.eclipse.jdt.annotation_2.1.0
一起使用
import java.util.Iterator;
import java.util.Map.Entry;
import java.util.Set;
import java.util.TreeMap;
import org.eclipse.jdt.annotation.NonNullByDefault;
import org.eclipse.jdt.annotation.Nullable;
@NonNullByDefault
public class NullAnnotationTest4 {
public static void main(String[] args) {
final TreeMap<@Nullable Integer, @Nullable String> treeMap = new TreeMap<>();
treeMap.put(3, "Test1");
treeMap.put(null, null);
//This produces the warning
final Set<@Nullable Entry<@Nullable Integer, @Nullable String>> set = treeMap.entrySet();
for (final Iterator<@Nullable Entry<@Nullable Integer, @Nullable String>> it = set.iterator(); it.hasNext(); ) {
final Entry<@Nullable Integer, @Nullable String> entry = it.next();
if (entry != null && entry.getKey() == null && entry.getValue() != null)
System.out.println(entry.getKey()+" is mapped to "+entry.getValue());
}
}
}
警告是:
Null type safety (type annotations):
The expression of type
'Set<Map.Entry<@Nullable Integer,@Nullable String>>'
needs unchecked conversion to conform to
'Set<Map.@Nullable Entry<@Nullable Integer,@Nullable String>>'
我尝试了几种@Nullable 和@NonNullable 的组合。甚至 ? extends
就像这里类似案例中所建议的那样:https://bugs.eclipse.org/bugs/show_bug.cgi?id=507779
但警告总是只会移动而不会完全消失。
更新:
我通过使用这一行摆脱了警告:
final Set<? extends @Nullable Entry<@Nullable Integer, @Nullable String>> set = treeMap.entrySet();
但我完全不知道为什么。在我看来,我欺骗了验证器以丢失轨道或其他东西,代码真的开始变得丑陋了。
完整的新代码:
import java.util.Iterator;
import java.util.Map.Entry;
import java.util.Set;
import java.util.TreeMap;
import org.eclipse.jdt.annotation.NonNullByDefault;
import org.eclipse.jdt.annotation.Nullable;
@NonNullByDefault
public class NullAnnotationTest4 {
public static void main(String[] args) {
final TreeMap<@Nullable Integer, @Nullable String> treeMap = new TreeMap<>();
treeMap.put(3, "Test1");
treeMap.put(null, null);
final Set<? extends @Nullable Entry<@Nullable Integer, @Nullable String>> set = treeMap.entrySet();
for (final Iterator<? extends @Nullable Entry<@Nullable Integer, @Nullable String>> it = set.iterator(); it.hasNext(); ) {
final Entry<@Nullable Integer, @Nullable String> entry = it.next();
if (entry != null && entry.getKey() == null && entry.getValue() != null)
System.out.println(entry.getKey()+" is mapped to "+entry.getValue());
}
}
}
更新 2矮子贴错代码了。
Set<@NonNull X>
和 Set<@Nullable X>
等问题类型的核心是不兼容的:两者都不能分配给另一个。
也就是说:如果你有一个 Set<@NonNull X>
客户期望 提取 非空元素,并且如果集合实际上是 Set<@Nullable X>
就会中断。相反,如果你有一个 Set<@Nullable X>
客户希望能够 插入 null
到集合中,如果集合实际上是 Set<@NonNull X>
就会中断。
每当您必须处理我们知识不足的 "legacy" 类型 Set<X>
时,这些注意事项都是相关的:它可能是 Set<@NonNull X>
或 Set<@Nullable X>
.类型检查必须考虑这两种可能性(客户可能依赖于任何一种假设,因为,例如,javadoc 可能会这样说)。
通常,在 Java 中,读取与写入问题通过使用有界通配符来解决:Set<? extends X>
确保读取访问将始终产生 "at least" X(或更好)。 Set<? super X>
确保插入新元素的要求是 "at most" X,即任何 X 或更好的元素都将被接受到集合中(无论实际列表的实际要求是什么)。
要将以上内容应用于空注释,只需说 Set<? extends @Nullable X>
即可接受旧集并支持从该集读取(值至少为 @Nullable X
,可能会更好,例如 @NonNull X
).
如果需要插入遗留集,请将其分配给 Set<? super @NonNull X>
类型的变量。这告诉类型检查器,@NonNull X
总是足以插入。
这就是为什么 Set<? extends @Nullable Entry<..>
接受 treeMap.entrySet()
的结果,它的类型实际上是 Set<Entry<@Nullable Integer, @Nullable String>>
。由于 entrySet()
.
的遗留签名,这里的内部类型参数完全由 treeMap
的声明注释,只有顶层类型参数 Entry
未指定
最后提到的也暗示了示例的 "real" 解决方案:使用外部注释来指示 entrySet()
实际上 returns @NonNull Set<@NonNull Entry<K,V>>
。有了这个 none 的通配符魔法就需要了。
如何消除此示例代码中的警告。
我将 Eclipse Neon 与 Java 1.8 和 org.eclipse.jdt.annotation_2.1.0
一起使用import java.util.Iterator;
import java.util.Map.Entry;
import java.util.Set;
import java.util.TreeMap;
import org.eclipse.jdt.annotation.NonNullByDefault;
import org.eclipse.jdt.annotation.Nullable;
@NonNullByDefault
public class NullAnnotationTest4 {
public static void main(String[] args) {
final TreeMap<@Nullable Integer, @Nullable String> treeMap = new TreeMap<>();
treeMap.put(3, "Test1");
treeMap.put(null, null);
//This produces the warning
final Set<@Nullable Entry<@Nullable Integer, @Nullable String>> set = treeMap.entrySet();
for (final Iterator<@Nullable Entry<@Nullable Integer, @Nullable String>> it = set.iterator(); it.hasNext(); ) {
final Entry<@Nullable Integer, @Nullable String> entry = it.next();
if (entry != null && entry.getKey() == null && entry.getValue() != null)
System.out.println(entry.getKey()+" is mapped to "+entry.getValue());
}
}
}
警告是:
Null type safety (type annotations):
The expression of type
'Set<Map.Entry<@Nullable Integer,@Nullable String>>'
needs unchecked conversion to conform to
'Set<Map.@Nullable Entry<@Nullable Integer,@Nullable String>>'
我尝试了几种@Nullable 和@NonNullable 的组合。甚至 ? extends
就像这里类似案例中所建议的那样:https://bugs.eclipse.org/bugs/show_bug.cgi?id=507779
但警告总是只会移动而不会完全消失。
更新:
我通过使用这一行摆脱了警告:
final Set<? extends @Nullable Entry<@Nullable Integer, @Nullable String>> set = treeMap.entrySet();
但我完全不知道为什么。在我看来,我欺骗了验证器以丢失轨道或其他东西,代码真的开始变得丑陋了。
完整的新代码:
import java.util.Iterator;
import java.util.Map.Entry;
import java.util.Set;
import java.util.TreeMap;
import org.eclipse.jdt.annotation.NonNullByDefault;
import org.eclipse.jdt.annotation.Nullable;
@NonNullByDefault
public class NullAnnotationTest4 {
public static void main(String[] args) {
final TreeMap<@Nullable Integer, @Nullable String> treeMap = new TreeMap<>();
treeMap.put(3, "Test1");
treeMap.put(null, null);
final Set<? extends @Nullable Entry<@Nullable Integer, @Nullable String>> set = treeMap.entrySet();
for (final Iterator<? extends @Nullable Entry<@Nullable Integer, @Nullable String>> it = set.iterator(); it.hasNext(); ) {
final Entry<@Nullable Integer, @Nullable String> entry = it.next();
if (entry != null && entry.getKey() == null && entry.getValue() != null)
System.out.println(entry.getKey()+" is mapped to "+entry.getValue());
}
}
}
更新 2矮子贴错代码了。
Set<@NonNull X>
和 Set<@Nullable X>
等问题类型的核心是不兼容的:两者都不能分配给另一个。
也就是说:如果你有一个 Set<@NonNull X>
客户期望 提取 非空元素,并且如果集合实际上是 Set<@Nullable X>
就会中断。相反,如果你有一个 Set<@Nullable X>
客户希望能够 插入 null
到集合中,如果集合实际上是 Set<@NonNull X>
就会中断。
每当您必须处理我们知识不足的 "legacy" 类型 Set<X>
时,这些注意事项都是相关的:它可能是 Set<@NonNull X>
或 Set<@Nullable X>
.类型检查必须考虑这两种可能性(客户可能依赖于任何一种假设,因为,例如,javadoc 可能会这样说)。
通常,在 Java 中,读取与写入问题通过使用有界通配符来解决:Set<? extends X>
确保读取访问将始终产生 "at least" X(或更好)。 Set<? super X>
确保插入新元素的要求是 "at most" X,即任何 X 或更好的元素都将被接受到集合中(无论实际列表的实际要求是什么)。
要将以上内容应用于空注释,只需说 Set<? extends @Nullable X>
即可接受旧集并支持从该集读取(值至少为 @Nullable X
,可能会更好,例如 @NonNull X
).
如果需要插入遗留集,请将其分配给 Set<? super @NonNull X>
类型的变量。这告诉类型检查器,@NonNull X
总是足以插入。
这就是为什么 Set<? extends @Nullable Entry<..>
接受 treeMap.entrySet()
的结果,它的类型实际上是 Set<Entry<@Nullable Integer, @Nullable String>>
。由于 entrySet()
.
treeMap
的声明注释,只有顶层类型参数 Entry
未指定
最后提到的也暗示了示例的 "real" 解决方案:使用外部注释来指示 entrySet()
实际上 returns @NonNull Set<@NonNull Entry<K,V>>
。有了这个 none 的通配符魔法就需要了。