具有非空队列的Python Queue.get(block = False)。它可以提升Queue.empty吗?

时间:2015-05-05 12:49:24

标签: python multithreading

我正在使用python的Queue.Queue来同步多个线程。首先,在队列中填充N个元素,如

N = 10
q = Queue.Queue()
for i in range(N):
  q.put(i)

然后,几个线程使用block = False

的队列中的元素
q.get(block=False)

我的问题是:先前对Queue.get()的调用是否可以在前N个调用中提升Queue.Empty?

谢谢!

1 个答案:

答案 0 :(得分:0)

N的第一次get()来电将成功;如果队列实际为空,q.get(block=False)只会引发Queue.Empty。线程对get的所有调用都是同步的,因此获得Queue使用的互斥锁的前N个线程将成功get来自Queue的项目。如果你有N + 1个或更多个主题,那么第N个以外的任何get都会提升Queue.Empty。如Eric所述,通过查看Queue代码的相关部分,可以很容易地看到这一点。

class Queue:
    """Create a queue object with a given maximum size.

    If maxsize is <= 0, the queue size is infinite.
    """
    def __init__(self, maxsize=0):
        self.maxsize = maxsize
        self._init(maxsize)
        self.mutex = _threading.Lock()
        self.not_empty = _threading.Condition(self.mutex)
        ... # Stuff we don't care about

    def get(self, block=True, timeout=None):
        self.not_empty.acquire() # Only on thread can hold this at a time
        try:
            if not block:
                if not self._qsize(): # If there's nothing in the Queue
                    raise Empty
            ... # Other stuff we don't care about, since you use block=False
            item = self._get()
            self.not_full.notify()
            return item
        finally:
            self.not_empty.release()

    def _init(self, maxsize):
        self.queue = deque()

    def _qsize(self, len=len):
        return len(self.queue)