为什么在spawn_n之后eventlet GreenPool不能调用func,除非waitall()?

此代码不打印任何内容:

def foo(i):
    print i

def main():
    pool = eventlet.GreenPool(size=100)
    for i in xrange(100):
        pool.spawn_n(foo, i)
    while True:
        pass

但是此代码显示数字:

def foo(i):
    print i

def main():
    pool = eventlet.GreenPool(size=100)
    for i in xrange(100):
        pool.spawn_n(foo, i)
    pool.waitall()
    while True:
        pass

唯一的区别是pool.waitall().在我看来,waitall()意味着要等到池中的所有绿色线程完成工作为止,但是无限循环会等待每个绿色线程,因此没有必要使用pool.waitall().

那么为什么会这样呢?

参考:http://eventlet.net/doc/modules/greenpool.html#eventlet.greenpool.GreenPool.waitall

解决方法:

在事件let GreenPool中创建的线程是绿色线程.这意味着它们都存在于操作系统级别的一个线程中,并且Python解释器处理它们之间的切换.仅当一个线程产生(故意为其他线程提供运行机会)或正在等待I / O时,才会发生这种切换.

当您的代码运行时:

while True:
    pass

…执行线程被阻塞–卡在该代码上–其他绿色线程无法调度.

当您改为运行时:

pool.waitall()

…eventlet确保它在等待时产生.

您可以通过稍微修改while循环以调用eventlet.sleep函数来模仿此行为,从而产生:

while True:
    eventlet.sleep()

如果您想在while:循环中等待池中的线程完成时做其他事情,这可能很有用.否则,只需使用pool.waitall()即可.

上一篇:在单个python进程中混合绿色线程和本机线程是否安全?


下一篇:eventlet设置超时时间