tornado学习笔记(二):如何在tornado中以异步的方式调用同步函数

问题
如何在tornado的coroutine中调用同步阻塞的函数

解决方案
使用python内置标准库的concurrent.futures.ThreadPoolExecutor和tornado.concurrent.run_on_executor

解决示例
a.使用concurrent.futures.ThreadPoolExecutor

#-*-coding:utf-8-*-
import time
from tornado.gen import coroutine
from tornado.ioloop import IOLoop
from concurrent.futures import ThreadPoolExecutor

def func():
    time.sleep(2)
    print(10)


def foo():
    time.sleep(1)
    print(15)

@coroutine
def main():
    pool = ThreadPoolExecutor(2)
    @coroutine
    def sync_func1():
        yield pool.submit(func,)

    @coroutine
    def sync_func2():
        yield pool.submit(foo,)
    t1 = time.time()
    yield [sync_func1(), sync_func2()]
    print(time.time() - t1)


if __name__ == '__main__':
    IOLoop.current().run_sync(main)

b.使用run_on_executor

#-*-coding:utf-8-*-
import os.path
import time
from tornado.gen import coroutine
from tornado.ioloop import IOLoop
from tornado.concurrent import run_on_executor
from concurrent.futures import ThreadPoolExecutor

class My(object):
    def __init__(self):
        self.executor = ThreadPoolExecutor(3)

    @run_on_executor
    def f(self):
        print(os.path.join(os.path.dirname(__file__), 'python'))
        time.sleep(2)
        print(10)

    @run_on_executor    
    def f1(self):
        time.sleep(1)
        print(15)

    @run_on_executor    
    def f2(self):
        time.sleep(1.5)
        print('hello, world!')

@coroutine
def main():
    m = My()
    t1 = time.time()
    yield [m.f1(), m.f2(), m.f()]
    print(time.time() - t1)


if __name__ == '__main__':
    IOLoop.current().run_sync(main)

总结
我们直接运行上面的两个同步的函数,耗时需要3秒。但我们利用了ThreadPoolExecutor之后,总耗时只需要2秒左右。下面是运行结果:
这里写图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值