美文网首页
python异步IO之协程

python异步IO之协程

作者: SimonJoe246 | 来源:发表于2018-12-07 22:06 被阅读0次

    异步和同步

    什么是异步?

    异步就是一项任务不一次性执行完,先执行第一段转而执行其他任务,等做好了准备,再回来执行剩下第二段。

    不连续的执行就叫做异步,相应的,连续的执行就叫做同步

    应用场景:

    在一个任务中包含打开文件或建立远程连接等耗时操作,若采用同步执行,则在读取文件或建立连接的过程中,程序只能干等着,什么事也做不了。

    如果使用异步执行,遇到耗时的阻塞则挂起,程序控制权交给别的任务,等别的任务执行完了或者也挂起,这时阻塞操作也已经执行完了,这时接着执行下面的操作即可。

    协程coroutine

    协程是由 async 关键字定义的对象,它的直接调用不会立即执行函数,而是返回一个写成对象,此对象只有注册到事件循环中,由事件循环调用。

    await

    await 是python3.5定义的,用以取代之前的 yield fromasync 定义一个协程, await 用于挂起阻塞的异步接口。

    看下面的例子:

    import asyncio, time
    
    start = time.time()
    
    now = lambda :time.time()
    
    async def do_something(s):
        print('waiting: %s s' % s)
        await asyncio.sleep(s)
        print('mission done {}'.format(s))
    
    loop = asyncio.get_event_loop()
    tasks = [do_something(2), do_something(1), do_something(4)]
    loop.run_until_complete(asyncio.wait(tasks))
    print(now()-start)
    loop.close()
    

    运行结果:

    waiting: 1 s
    waiting: 2 s
    waiting: 4 s
    mission done 1
    mission done 2
    mission done 4
    3.9893088340759277
    

    本来如果同步执行,程序至少需要7秒,但由于使用了协程,在遇到阻塞时程序挂起并未等待在阻塞处,转而执行其他的协程对象,从而减少程序运行时间。

    而且,如果我们打印当前线程名或发现,三个协程一直是在一个线程下执行的,也就是一个线程实现了并发操作。

    下面用一个形象的例子描述多协程并发执行的过程:

    晚自习,一个老师辅导多名学生,给A同学讲解完一道题的做法后,让其自己理解,做完这道题。

    做这道题是个耗时的操作,这时老师不必一直等他做完,可以去辅导B学生。

    给B讲解一道题,再让其理解做完,这时A的那道题已经做完了,可以回到A身边,讲解下一道题了。

    老师在A和B之间交替讲解,直到二者均完成其作业为止。

    其中,老师就是一线程,学生 A 和 B 是两个协程。学生做完所有作业是missionA 和 mission B。

    老师对每道题的讲解是正常的程序执行。

    听完老师讲解后,学生写每道题的过程是耗时的阻塞操作。

    相关文章

      网友评论

          本文标题:python异步IO之协程

          本文链接:https://www.haomeiwen.com/subject/tizxhqtx.html