java.util.Queue,它静默地丢弃null元素

时间:2013-02-20 01:03:54

标签: java

我正在寻找一个java.util.Queue实现或工厂方法,它为我提供了一个Queue静默地丢弃null个元素。

java.util.LinkedList不是解决方案,因为它允许队列 null元素和队列 null元素(... 。Queue 前进 - 不加直到它为空或头部位置有non - null元素。)
java.util.ArrayDeque不是解决方案,因为它在尝试添加NullPointerException元素时会抛出null

应该可以使用现有的Queue构建这样的Queue(现有的Queue可能包含null元素,这些元素会被新构建的{Queue删除1}}操作)。

那里已经有一个强大的解决方案吗?

2 个答案:

答案 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>