我正在寻找一个java.util.Queue
实现或工厂方法,它为我提供了一个Queue
静默地丢弃null
个元素。
java.util.LinkedList
不是解决方案,因为它允许队列 null
元素和队列 null
元素(... 。Queue
前进 - 不加直到它为空或头部位置有non
- null元素。)
java.util.ArrayDeque
不是解决方案,因为它在尝试添加NullPointerException
元素时会抛出null
。
应该可以使用现有的Queue
构建这样的Queue
(现有的Queue
可能包含null
元素,这些元素会被新构建的{Queue
删除1}}操作)。
那里已经有一个强大的解决方案吗?
答案 0 :(得分:3)
虽然我发现这并没有直接回答你的问题,但如果找不到实施并决定自己上课,那么这个答案应该适用。
由于子类不符合超类的预期实现和使用(例如,super可能依赖于能够添加null元素,因此这会打破它),我会阻止“Hot Licks”建议的子类化。此外,您通过更改主要实施细节来打破Is-A原则。
我建议您使用合成,您可以通过自己的方法提供适当的方法,这可能会在必要时改变行为。
阅读Effective Java Chapter 16中的更多内容。
答案 1 :(得分:1)
没有理由必须创建一个全新的子类,您可以在创建实例时覆盖所需的方法。
以下是一个例子:
final ArrayDeque<String> nonNullDeque = new ArrayDeque<String>() {
@Override
public void addFirst(final String s) {
if (s != null) { super.addFirst(s); }
}
@Override
public boolean add(final String s) {
return s != null && super.add(s);
}
@Override
public void addLast(final String s) {
if (s != null) { super.addLast(s); }
}
};
这就是你有能力用你自己的行为覆盖方法的全部原因,超类的内部工作应该是一个黑盒子,你与它的契约是接受参数并返回其结果接口支持,不支持其内部工作。
就个人而言,我会更进一步,而不是检查空值,并使用Google findbugs library使用JSR = 305 @Nonnull
注释。注释不仅会在代码获得机会之前捕获null
,它会隐含地记录您的意图。
public void addFirst(@Nonnull final String s) {
if (s != null) { super.addFirst(s); }
}
Maven依赖在Central Repo中,因此无需添加到项目中。
<dependency>
<groupId>com.google.code.findbugs</groupId>
<artifactId>jsr305</artifactId>
<version>2.0.1</version>
</dependency>