2015-07-10 44 views
0

我想要一个线程安全的容器,阻止调用方,直到项目变得可用。物品将以每秒1000秒的速度添加到此容器中,但不会以相同的速度排出。因此,我希望容器不允许重复。 我写了一个关于LinkedBlockingQueue的简单包装,但很快就意识到我已经重新创建了经典的生产者 - 消费者的死锁。这是我写的:BlockingQueue像容器,不允许重复

public class ActivityListener { 
    private final BlockingQueue<ID> activeItems = new LinkedBlockingQueue<>(); 

    public synchronized ID take() throws InterruptedException { 
     return activeItems.take(); 
    } 

    public synchronized void registerActivity(final ID item) { 
     if (!activeItems.contains(item)) { 
      activeItems.add(item); 
     } 
    } 

    public synchronized boolean isItemActive(final ID item) { 
     return activeItems.contains(item); 
    } 
} 

我找不到一个既定的解决我的问题,并希望得到任何帮助。

+0

你需要一个_full_的BlockingQueue的实现,或只是'把()'和'采取()'? – jtahlborn

+0

我只需要把和 – user1071840

+0

可能的重复:http://stackoverflow.com/questions/3120495/concurrent-set-queue – wickstopher

回答

0

覆盖任何BlockingQueue实现的add()和put()方法,首先检查元素是否已经在队列中。

喜欢的东西 -

@Override 
public boolean add(T obj) { 
    if (contains(obj)) 
     return true; 
    return super.add(obj); 
} 
+0

这不是线程安全的,不幸的是可能不能这样做(至少在一般情况下案件)。 – jtahlborn

+0

另外,当一个对象没有添加到集合中时,从类集接口上的add方法返回true是非惯用的。 – wickstopher