立即启动Python asyncio courutines执行

时间:2014-11-29 01:22:16

标签: python asynchronous hacklang

我正在尝试了解Python asyncio 模块。它似乎比其他语言中的类似功能复杂得多。

以下是文档中的excerpt

  

调用一个协程不会启动它的代码运行 - 它只是一个生成器,并且该调用返回的协程对象实际上是一个生成器对象,在迭代它之前它不会执行任何操作。在协程对象的情况下,有两种基本的方式来启动它运行:来自另一个协同程序的协同程序的调用yield(假设另一个协同程序已在运行!),或使用async()函数或BaseEventLoop计划执行它。 create_task()方法。

     

协程(和任务)只能在事件循环运行时运行。

这是否意味着使用Hack实现类似here的类似执行流程?

function main() : void
{
    $info = Vector {};
    for ($i = 0; $i < 5; $i++) {
        $info[] = genInfo($i);
    }

    echo '[main] Calling Async Function'."\n";
    $asyncCall = GenVectorWaitHandle::create($info);

    echo '[main] Doing whatever...'."\n";

    echo '[main] Time To Request Async Return Information'."\n";
    $output = $asyncCall->join();

    // Output Vector Data
    foreach ($output as $key => $value)
    {
        echo '['.$key.'] => '.$value."\n";
    }
}

async function genInfo(int $id): Awaitable<String> {
    echo '[genInfo] Generating '.$id."\n";

    $tmp = [];
    $tmp['id'] = $id;
    $tmp['start'] = date('H:i:s');

    //do some heavy working.
    await SleepWaitHandle::create(mt_rand(1000000,15*1000000));

    $tmp['end'] = date('H:i:s');

    echo "[genInfo] Completed $id\n";

    return json_encode($tmp);
}

main();

/*
 * This is a modified example from http://kernelcurry.com/blog/asynchronous-hack/
 */

//Output
[genInfo] Generating 0
[genInfo] Generating 1
[genInfo] Generating 2
[genInfo] Generating 3
[genInfo] Generating 4
[main] Calling Async Function
[main] Doing whatever...
[main] Time To Request Async Return Information
[genInfo] Completed 0
[genInfo] Completed 3
[genInfo] Completed 2
[genInfo] Completed 1
[genInfo] Completed 4
[0] => {"id":0,"start":"19:46:00","end":"19:46:03"}
[1] => {"id":1,"start":"19:46:00","end":"19:46:08"}
[2] => {"id":2,"start":"19:46:00","end":"19:46:05"}
[3] => {"id":3,"start":"19:46:00","end":"19:46:04"}
[4] => {"id":4,"start":"19:46:00","end":"19:46:08"}

如您所见,genInfo()执行后立即开始执行,并在 await 语句中获得收益。我认为这样的执行流程比使用Python this one更自然。

有没有办法在Python中实现相同的目标?

我尝试迭代coroutines生成器一次(为了让它们执行并接近第一个yield),然后将它们传递给loop.run_until_complete(),但没有成功。

0 个答案:

没有答案