PYTHON ASYNCIO: FUTURE, TASK AND THE EVENT LOOP
2016-05-11 14:17
706 查看
from :http://masnun.com/2015/11/20/python-asyncio-future-task-and-the-event-loop.html
Event Loop
On any platform, when we want to do something asynchronously, it usually involves an event loop. An event loop is a loop that can register tasks to be executed, execute them, delay or even cancel them and handle different events related to these operations. Generally, we schedule multiple async functions to the event loop. The loop runs one function, while that function waits for IO, it pauses it and runs another. When the first function completes IO, it is resumed. Thus two or more functions can co-operatively run together. This the main goal of an event loop.The event loop can also pass resource intensive functions to a thread pool for processing. The internals of the event loop is quite complex and we don’t need to worry much about it right away. We just need to remember that the event loop is the mechanism through which we can schedule our async functions and get them executed.
Futures / Tasks
If you are into Javascript too, you probably know about Promise. In Python we have similar concepts – Future/Task. A Future is an object that is supposed to have a result in the future. A Task is a subclass of Future that wraps a coroutine. When the coroutine finishes, the result of the Task is realized.Coroutines
We discussed Coroutines in our last blog post. It’s a way of pausing a function and returning a series of values periodically. A coroutine can pause the execution of the function by using theyield
yield fromor
await(python 3.5+) keywords in an expression. The function is paused until the
yieldstatement actually gets a value.
Fitting Event Loop and Future/Task Together
It’s simple. We need an event loop and we need to register our future/task objects with the event loop. The loop will schedule and run them. We can add callbacks to our future/task objects so that we can be notified when a future has it’s results.Very often we choose to use coroutines for our work. We wrap a coroutine in Future and get a Task object. When a coroutine
yields, it is paused. When it has a value, it is resumed. When it
returns, the Task has completed and gets a value. Any associated callback is run. If the coroutine raises an exception, the Task fails and not resolved.
So let’s move ahead and see example codes.
Python
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 | import asyncio @asyncio.coroutine def slow_operation(): # yield from suspends execution until # there's some result from asyncio.sleep yield from asyncio.sleep(1) # our task is done, here's the result return 'Future is done!' def got_result(future): print(future.result()) # Our main event loop loop = asyncio.get_event_loop() # We create a task from a coroutine task = loop.create_task(slow_operation()) # Please notify us when the task is complete task.add_done_callback(got_result) # The loop will close when the task has resolved loop.run_until_complete(task) |
@asyncio.coroutinegets us the default event loop
loop.create_task(slow_operation())creates a task from the coroutine returned by
slow_operation()
task.add_done_callback(got_result)adds a callback to our task
loop.run_until_complete(task)runs the event loop until the task is realized. As soon as it has value, the loop terminates
The
run_until_completefunction is a nice way to manage the loop. Of course we could do this:
Python
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | import asyncio async def slow_operation(): await asyncio.sleep(1) return 'Future is done!' def got_result(future): print(future.result()) # We have result, so let's stop loop.stop() loop = asyncio.get_event_loop() task = loop.create_task(slow_operation()) task.add_done_callback(got_result) # We run forever loop.run_forever() |
相关文章推荐
- 利用Python自动发送邮件
- 模块yaml
- 利用Python抓取图片
- Python&pip install中出现的asciii码错误的问题
- python05-09
- python全栈开发day1
- Python魔法 - MetaClass
- Python 手记
- Python numpy生成矩阵、串联矩阵
- Python numpy 平方、乘方和平方根函数
- Python运行报错IndentationError: unindent does not match any outer indentation level
- Python实现杨辉三角形
- Python tar.gz格式压缩、解压
- Python获取当前目录下所有文件的绝对路径并存储在文件中
- Python enumerate
- Python开发环境配置及工具库安装
- Python学习笔记:条件、循环
- python 多行匹配
- Python的functools模块
- python self introspection