3

据我了解,gevent 中的池的想法是在任何时候将并发请求的总数限制为数据库或 API 或类似的。

假设我有这样的代码,其中我产生的绿叶比我在以下空间中的空间还多Pool

import gevent.pool

pool = gevent.pool.Pool(50)
jobs = []
for number in xrange(300):
    jobs.append(pool.spawn(do_something, number))

total_result = [x.get() for x in jobs]

尝试产生第 51 个请求时的实际行为是什么?第 51 个请求何时处理?

4

1 回答 1

7

pool 类使用信号量来计算活动的 greenlets,size在构造函数中使用 count 进行初始化:

class Pool(Group):

    def __init__(self, size=None, greenlet_class=None):
        if size is not None and size < 1:
            raise ValueError('Invalid size for pool (positive integer or None required): %r' % (size, ))
        Group.__init__(self)
        self.size = size
        if greenlet_class is not None:
            self.greenlet_class = greenlet_class
        if size is None:
            self._semaphore = DummySemaphore()
        else:
            self._semaphore = Semaphore(size)

每次spawn()被调用时,它都会尝试获取信号量:

    def spawn(self, *args, **kwargs):
        self._semaphore.acquire()
        try:
            greenlet = self.greenlet_class.spawn(*args, **kwargs)
            self.add(greenlet)
        except:
            self._semaphore.release()
            raise
        return greenlet

如果池已满,则被调用的 greenlet 将等待_semaphore.acquire()待命。每当任何 greenlets 结束执行时,就会释放信号量:

    def discard(self, greenlet):
       Group.discard(self, greenlet)
       self._semaphore.release()

So in your case, I'd expect the 51st request to be handled (or started, to be precise) as soon as any of the first 50 requests is done.

于 2013-01-15T15:49:28.793 回答