0

我有一个while循环来检查包含程序要执行的命令的arraylist是否为空。显然,如果不是空的,它会做一些事情,但如果是现在,我只有一个 Thread.sleep(1000) 用于其他。这使得与之交互的任何东西都相当缓慢。有没有办法让它运行的线程阻塞,直到添加新命令?(它在自己的线程中运行,所以这对我来说似乎是最好的解决方案)或者有更好的解决方案吗?

4

3 回答 3

5

您可以使用wait()and让向列表中添加notify()某些内容的线程通知消费者线程有要读取的内容。但是,这需要适当的同步等。

但是解决问题的更好方法是使用 aBlockingQueue代替。根据定义,它们是同步类,出队将适当地阻塞并在添加内容时唤醒。LinkedBlockingQueue如果您希望队列不受限制,这是一个很好的类。当ArrayBlockingQueue您希望将有限数量的项目存储在队列中(或LinkedBlockingQueue将整数传递给构造函数)时,可以使用 。如果queue.add(...)队列已满,则如果队列已满,则将阻塞。

BlockingQueue<Message> queue = new LinkedBlockingQueue<Messsage>();
...
// producer thread(s) add a message to the queue
queue.add(message);
...
// consumer(s) wait for a message to be added to the queue and then removes it
Message message = queue.take();
...
// you can also wait for certain amount of time, returns null on timeout
Message message = queue.poll(10, TimeUnit.MINUTES);
于 2012-07-12T17:44:59.103 回答
3

将 aBlockingQueue<E>用于您的命令。
在上面的链接中有一个很好的例子来说明如何使用它。

于 2012-07-12T17:45:32.363 回答
2

更好的解决方案是使用 ExecutorService。这结合了一个队列和一个线程池。

// or use a thread pool with multiple threads.
ExecutorService executor = Executors.newSingleThreadExecutor();

// call as often as you like.    
executor.submit(new Runnable() {
    @Override
    public void run() {
        process(string);
    }
});

// when finished
executor.shutdown();
于 2012-07-12T17:54:24.027 回答