浅析python协程相关概念

 更新时间:2018年01月20日 10:18:12   投稿:laozhang  
本篇文章给大家分析了一下python协程的概念以及代码相关实例,有兴趣的朋友跟着小编学习下吧。

这篇文章是读者朋友的python协程的学习经验之谈,以下是全部内容:

协程的历史说来话长,要从生成器开始讲起。

如果你看过我之前的文章python奇遇记:迭代器和生成器 ,对生成器的概念应该很了解。生成器节省内存,用的时候才生成结果。

 

# 生成器表达式
a = (x*x for x in range(10))
# next生成值
next(a()) # 输出0
next(a()) # 输出1
next(a()) # 输出4

与生成器产出数据不同的是,协程在产出数据的同时还可以接收数据,具体来说就是把yield 放在了表达式的右边。我们可以使用.send() 把数据发送给协程函数。

 def writer():
  print('-> coroutine started')
  for i in range(8):
    w = yield
    print(i+w)

w = writer()
# 本质还是生成器
>>> w
<generator object writer at 0x000002595BC57468>
# 首先要用next()把协程激活
>>> next(w)
-> coroutine started
# 发送数据
>>> w.send(1)
1
# send到第八次之后会抛出异常
# 因为协程已经结束了
---------------------------------------------------------------------------
StopIteration               Traceback (most recent call last)

第一步必须使用next() 激活协程函数,这样才能在下一步使用.send() 发送数据。

可以看到,在第8次接收完数据之后,会产生结束的异常,因为程序流程结束了,这是正常现象。加个异常处理即可。如果需要在两个协程间传递数据呢?

def writer():
  while True:
    w = yield
    print('>>', w)

def writer_wrapper(coro):
  # 激活
  next(coro)
  while True:
    # 异常处理
    try:
      x = yield
      # 发送数据给writer
      coro.send(x)
    except StopIteration:
      pass
w = writer()
wrap = writer_wrapper(w)
# 激活
next(wrap)
for i in range(4):
  wrap.send(i)
# 输出
>> 0
>> 1
>> 2
>> 3

上面的代码中,数据首先传递到writer_wrapper,之后再传递到writer 。

data——>writer_wrapper——>writer

可以这么写,不过,又要预先激活,又要加异常,看起来有点麻烦啊。yield from 的出现可以解决这个问题,同样是传递数据:

def writer():
  while True:
    w = yield
    print('>>', w)
def writer_wrapper2(coro):
  yield from coro

一行代码解决问题。

总之,yield from相当于提供了一个通道,使得数据可以在协程之间流转 。writer_wrapper2 中使用yield from coro时,coro此时获得控制权,在我们.send() 数据时,writer_wrapper2 被阻塞,直到writer 打印出结果。

在这个阶段,协程本质上还是由生成器构成的。

即使我们使用yield from 简化了流程,协程和生成器的知识理解起来还是有点懵逼,而且yield from 用在异步编程中有诸多不顺(asyncio以前就是用yield from),于是在3.5版本的python中,弃用了yield from ,新加入了两个关键字async 和await ,同时协程不再是生成器类型,而是原生的协程类型。

现在我们定义一个协程要像下面这样:

async def func():
  await 'some code'

不用于异步的协程该怎么用,我还不知道。所以,协程的介绍到这里就结束啦。感谢你对脚本之家的支持。

相关文章

  • Python MNIST手写体识别详解与试练

    Python MNIST手写体识别详解与试练

    MNIST(官方网站)是非常有名的手写体数字识别数据集,在Tensorflow的官方网站里,第一个就拿它来做实战讲解,咱们也以此作为开始的项目
    2021-11-11
  • python中HTMLParser模块知识点总结

    python中HTMLParser模块知识点总结

    在本篇文章里小编给大家整理的是一篇关于python中HTMLParser模块知识点内容,有兴趣的朋友们可以跟着学习下。
    2021-01-01
  • 手把手教你用322行Python代码编写贪吃蛇游戏

    手把手教你用322行Python代码编写贪吃蛇游戏

    最近在学Python,想做点什么来练练手,命令行的贪吃蛇一般是C的练手项目,但是一时之间找不到别的,就先做个贪吃蛇来练练简单的语法,下面这篇文章主要给大家介绍了关于如何用322行Python代码编写贪吃蛇游戏的相关资料,需要的朋友可以参考下
    2023-02-02
  • pytorch无坑安装CPU版小白教程(配gpu版链接、conda命令教程)

    pytorch无坑安装CPU版小白教程(配gpu版链接、conda命令教程)

    pip安装无论是cpu还是gpu的pytorch安装,其实官方给了很好的安装流程,本文主要介绍了pytorch无坑安装CPU版小白教程,具有一定的参考价值,感兴趣的可以了解一下
    2024-03-03
  • 用yum安装MySQLdb模块的步骤方法

    用yum安装MySQLdb模块的步骤方法

    在python2.7版本中,MySQLdb模块还不是python的内置模块,但是MySQLdb模块又是Python与MySQL连接的桥梁,对于作为MySQL DBA又很喜欢Python语言的我来说,MySQLdb真的是必需品呢。所以就需要自己进行安装了,这篇文章就给大家详细介绍了关于用yum安装MySQLdb模块的步骤。
    2016-12-12
  • Python sqlite3查询操作过程解析

    Python sqlite3查询操作过程解析

    这篇文章主要介绍了Python sqlite3查询操作过程解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2020-02-02
  • 使用Tkinter制作信息提示框

    使用Tkinter制作信息提示框

    这篇文章主要介绍了使用Tkinter制作信息提示框的相关资料,需要的朋友可以参考下
    2020-02-02
  • python数据分析工具之 matplotlib详解

    python数据分析工具之 matplotlib详解

    对于 Python 来说,matplotlib 是最著名的绘图库,它主要用于二维绘图,当然也可以进行简单的三维绘图。这篇文章主要介绍了python数据分析工具之 matplotlib的相关知识,需要的朋友可以参考下
    2020-04-04
  • pygame游戏之旅 游戏中添加显示文字

    pygame游戏之旅 游戏中添加显示文字

    这篇文章主要为大家详细介绍了pygame游戏之旅的第5篇,教大家如何在游戏中添加显示文字,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2018-11-11
  • 浅析Python基础-流程控制

    浅析Python基础-流程控制

    Python编程语言的作用非常强大,而且其应用方便的特点也对开发人员起到了非常大的作用。在这里我们就可以先从Python流程控制关键字的相关概念开始了解,从而初步掌握这一语言的特点
    2016-03-03

最新评论