Что Python эквивалентно C # ContinueWith () - PullRequest
0 голосов
/ 11 июня 2018

Что представляет собой Python-эквивалент этого кода?

var firstTask = new Task(() => Foo());
var secondTask = firstTask.ContinueWith((fooResult) => Bar(fooResult));
firstTask.Start();

Я предполагаю, что он будет использовать библиотеку asyncio.Я знаю, как создать задачу в Python, но не могу найти простой пример того, что делает то же самое, что и C # ContinueWith ()

1 Ответ

0 голосов
/ 11 июня 2018

Вы можете использовать функцию регистрации обратного вызова Future.add_done_callback() , чтобы сделать то же самое;отображение поддержки лямбда-функции будет:

import asyncio

def continue_task_with(task, callback, *, loop=None):
    """When a task completes, schedule a new task.

    The new task is created by calling the callback with the result of
    the first task.

    """
    def done_callback(fut):
        asyncio.ensure_future(callback(fut), loop=loop)
    task.add_done_callback(done_callback)

foo_task = asyncio.ensure_future(foo())
continue_task_with(foo_task, lambda result: bar(result))
asyncio.get_event_loop().run_forever()

Так вот:

  • Создает задачу для Foo()
  • Регистрирует обратный вызов для вызова этой функциикогда задача выполнена.
  • Обратный вызов получает объект задачи и передает этот объект задачи в качестве первого аргумента лямбда-функции, которая создает сопрограмму Bar() из этого.Затем результат лямбды планируется как новая задача для запуска.
  • Затем планирует задачу Foo();когда эта задача завершается, вызывается обратный вызов Bar() для запуска Bar().

Демо:

>>> async def foo():
...     print('Running foo')
...     await asyncio.sleep(1)
...     print('Completing foo')
...     return 42
...
>>> async def bar(foo_task):
...     print('Running bar')
...     if not (foo_task.cancelled() or foo_task.exception()):
...         print('Foo completed successfully, it received', foo_task.result())
...     asyncio.get_event_loop().stop()
...
>>> foo_task = asyncio.ensure_future(foo())
>>> continue_task_with(foo_task, lambda result: bar(result))
>>> asyncio.get_event_loop().run_forever()
Running foo
Completing foo
Running bar
Foo completed successfully, it received 42
...