包装Python线程的库

时间:2013-05-17 18:00:14

标签: python

哪些库存在为Python中的并发提供更高级别的接口?我不一定要使用多个内核 - 如果GIL序列化所有内容,那对我来说没问题。我只想要一个更平滑/更高级别的并发接口。

我的应用程序正在编写我们软件的测试,有时我想比较运行几个模拟用户,以及对后端进行更改的代码。如果,比方说,我可以做这样的事情会很棒:

setup_front_end()
setup_back_end()
parallel:
   while some_condition():
      os.system('wget http://...')
      sleep(1)
   for x in xrange(10):
      os.system('top >> top.log')
      sleep(1)
   for x in xrange(100):
      mess_with_backend()

上面代码中的想法是我们启动3个线程,第一个运行:

while some_condition():
   os.system('wget http://...')
   sleep(1)

第二个循环运行第二个循环,第三个循环运行第三个循环。

我知道它不会那么简单,但是有什么东西可以让苦差事不能写出函数,旋转线程,加入它们等等吗?

2 个答案:

答案 0 :(得分:1)

threading模块外,您还应该查看concurrent.futures模块(对于py2是backport)。

它提供了随时可用的线程/进程池实现,并允许您编写高效的并发代码。因为它为线程和多处理提供了统一的API,所以如果需要,它允许您在两者之间轻松切换。

答案 1 :(得分:0)

如果您只想隐藏创建线程和设置参数的复杂性,请创建一个简单的装饰器并将其用于您的功能:

async.py:

from threading import Thread
class async(object):
    def __init__(self, func):
        self.func = func

    def __call__(self, *args, **kwargs):
        Thread(target=self.func, args=args, kwargs=kwargs).start()

这只是一个非常简单的函数包装器,它创建一个新的Thread并在Thread中执行该函数。如果需要,您可以轻松地将其调整为使用进程而不是线程。

main.py:

import time
from async import async

@async
def long_function(name, seconds_to_wait):
    print "%s started..." % name
    time.sleep(seconds_to_wait)
    print "%s ended after %d seconds" % (name, seconds_to_wait)

if __name__ == '__main__':
    long_function("first", 3)
    long_function("second", 4)
    long_function("third", 5)

只需使用@async修饰您的函数,就可以异步调用它。

在您的情况下:只需将循环包裹在函数中并使用@async进行装饰即可。

有关完整功能的异步装饰,请查看:http://wiki.python.org/moin/PythonDecoratorLibrary#Asynchronous_Call