• python协整与异步调用,压榨程序的摸鱼时间——异步改写一般程序(1)


    这篇博客简单的体会一下异步执行的感觉,并且改写一个常见的操作,理解异步的使用场景。

    异步的含义是:在程序有一些需要等待的时候,把继续运行的权利交出去,然后等到某个条件达成后再重新申请继续执行,它是相对于“同步”而出现的词。

    同步与异步的区别:

    类比成生活就是:一个小人,有两个作业:1. 线上平板刷课10分钟;2. 做口算题5分钟

    • 同步:小人,先刷课,用了10分钟,然后做口算题,用了5分钟,一共耗时15分钟
    • 异步:小人,平板挂着课程,去做口算题,用了5分钟,这时线上课程也过了5分钟,所以只需要再等5分钟即可完成作业,一共耗时10分钟

    异步与并行的区别:

    • 并行:变出三头六臂同时进行所有任务
    • 异步:任务还是一个一个完成,但疯狂压榨自己可能空闲的一切时间,在多个任务之间来回切换,赶进度

    常规顺序执行的函数

    对于一个如下的一般的程序:

    import time
    
    def my_task(number):
        print("begin task {} 时间:{}".format(number, time.time()))
        time.sleep(1)
        print('====== task {} 时间:{} ======='.format(number, time.time()))
    
    
    if __name__ == '__main__':
        for i in range(5):
            my_task(i)
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11

    得到的结果是:

    begin task 0 时间:1658886603.399502
    ====== task 0 时间:1658886604.399808 =======
    begin task 1 时间:1658886604.39987
    ====== task 1 时间:1658886605.4036212 =======
    begin task 2 时间:1658886605.4036832
    ====== task 2 时间:1658886606.408043 =======
    begin task 3 时间:1658886606.4081228
    ====== task 3 时间:1658886607.408743 =======
    begin task 4 时间:1658886607.4087849
    ====== task 4 时间:1658886608.413343 =======
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10

    程序按照既定的程序,按部就班的循序执行并得到想要的结果

    用异步操作改写函数

    改写的步骤如下:

    1. 导入异步操作的包(python3.5+):import asyncio
    2. 在可能需要交出控制权的函数前面添加async关键词
    3. 在函数内部可以交出控制权的函数前添加await关键词
    4. 最后通过一个普通函数的asyncio.get_event_loop()执行异步操作
    import time
    import asyncio
    
    
    async def my_async_task(number):
        print("begin task {} 时间:{}".format(number, time.time()))
        # await 是主动告诉程序在这里可以把程序的使用权交出去
        # 使用 asyncio.sleep(1) 是指模拟1秒的等待操作
        await asyncio.sleep(1)
        print('====== task {} 时间:{} ======='.format(number, time.time()))
    
    
    if __name__ == '__main__':
        loop = asyncio.get_event_loop()
        tasks = []
        for i in range(5):
            tasks.append(my_async_task(i))
        loop.run_until_complete(asyncio.wait(tasks))
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18

    得到的结果如下:

    begin task 3 时间:1658906069.224732
    begin task 0 时间:1658906069.224763
    begin task 4 时间:1658906069.224777
    begin task 1 时间:1658906069.224789
    begin task 2 时间:1658906069.224799
    ====== task 3 时间:1658906070.2289789 =======
    ====== task 0 时间:1658906070.2290099 =======
    ====== task 4 时间:1658906070.229023 =======
    ====== task 1 时间:1658906070.229034 =======
    ====== task 2 时间:1658906070.229046 =======
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10

    可以看到:

    1. 程序在执行到await时,都主动交出了程序的控制权,并继续执行循环操作
    2. 在循环的函数里是线性的执行,但是执行顺序是随机的

    因此,异步操作可以使用:

    1. 任意的函数都可以使用异步操作,因为在函数内部是线性操作

    2. 异步的函数就像是一个圈子,圈子里的任务需要加上async关键词,这些任务不能摸鱼,异步之外的函数没有要求。异步操作的内、外通过如下代码衔接:

          loop = asyncio.get_event_loop()
          tasks = []
          for i in range(5):
              tasks.append(my_async_task(i))
          loop.run_until_complete(asyncio.wait(tasks))
      
      • 1
      • 2
      • 3
      • 4
      • 5

    以上便是异步操作的基本模版,后续的内容会继续深入,并用异步操作改写任意的代码

    异步操作是比较高阶的用法,也是能够有效发挥程序效率的一个方法。执行异步的函数前后逻辑对大家的逻辑要求比较高,不是很容易梳理逻辑的,需要慢慢理解和练习

  • 相关阅读:
    第61章 Jquery JSON Table EntityFrameworkCore自动生成数据库
    Configuration涉及的Full&Lite模式
    人物故事 | 回顾美人建筑师,致世界建筑日
    PHP:表达式
    计算机毕业设计 基于Vue的米家商城系统的设计与实现 Java实战项目 附源码+文档+视频讲解
    无多余电源工业环境如何实现远程维护
    Java之juc旅途-atomic(五)
    基于微信小程序+ JAVA后端实现的【医院挂号预约系统】 设计与实现 (内附设计LW + PPT+ 源码+ 演示视频 下载)
    ArcGIS Pro SDK (七)编辑 5 编辑已完成事件
    【SQL语法基础】什么是SQL的聚集函数,如何利用它们汇总表的数据?
  • 原文地址:https://blog.csdn.net/weixin_35757704/article/details/126008280