首先,这是Java 7 的 Collections.checked*添加的行为:
由于 null 被认为是任何引用类型的值,因此返回的集合允许在支持集合时插入 null 元素。
不过,这似乎没有在兼容性文档中列出。演示:
public class MyAPI {
private Set<Polygon> polygons = new Collections.checkedSet(new HashSet<Polygon>(), Polygon.class);
public Set<Polygon> getPolygons() {
return polygons;
}
}
public class MyAPITest {
// This JUnit test passes when using Java 6 or earlier, but fails for Java 7.
@Test(expected=NullPointerException.class)
public void testAddNullPolygon() {
new MyAPI().getPolygons().add(null);
}
}
如您所见,我正在编写一个 API,它公开了一个Set
供客户端代码填充的 API。根据我的阅读,这是Collections.checkedCollection
etc 的用例之一:添加的运行时检查有助于防止插入奇怪的东西。
我已经更改了我的 API 以处理空值,但我担心客户端代码有时会抛出 NPE,有时不会,这取决于最终用户运行的 Java 版本。就是感觉破了。理想情况下,我想保留旧行为,防止在插入时出现空值。
我想我的选择是:
完全放弃运行时检查。
不用担心,相信客户端代码永远不会插入空值。
声明我的 API 只支持 JRE 7。
使用 Guava,它看起来很棒,但它是我的 API 会背负的额外依赖项。
滚动我自己的 Set 包装器,它强制执行 null 和类型检查。
我缺少的其他一些更优雅的解决方案。
任何指导将不胜感激!