今天通过一个简单的并行任务代码来分析 python 与 node.js 协程 async/await 使用的差异,源码很简单都是并行执行两个任务,await 等待执行结果。
源码与执行
- node.js
var sleep = function (time) {
return new Promise(function (resolve, reject) {
setTimeout(function () {
resolve();
}, time);
});
};
async function exec() {
await sleep(2000);
}
async function go() {
console.log(Date.now())
c1 = exec()
c2 = exec()
console.log(c1, c2)
await c1;
await c2;
console.log(Date.now())
}
go();
执行结果
1579175786988
Promise { <pending> } Promise { <pending> }
1579175788998
- python
import asyncio
import time
async def exec():
await asyncio.sleep(2)
if __name__ == "__main__":
async def go():
print(time.time())
c1 = exec()
c2 = exec()
print(c1, c2)
await c1
await c2
print(time.time())
asyncio.run(go())
执行结果
1579175904.634322
<coroutine object exec at 0x107ba0170> <coroutine object exec at 0x107ba0320>
1579175908.636878
结果分析
执行后发现 node.js 执行时间为 2s,而 python 执行时间为 4s,由此可见 node.js 的 Promise 是并行执行,而 python 的 Coroutine object 并没有并行执行,接下来我们修改一下 python 的源码:
import asyncio
import time
async def exec():
await asyncio.sleep(2)
if __name__ == "__main__":
async def go():
print(time.time())
c1 = asyncio.create_task(exec())
c2 = asyncio.create_task(exec())
print(c1, c2)
await c1
await c2
print(time.time())
asyncio.run(go())
执行结果
1579175984.749123
<Task pending coro=<exec() running at /Users/liujian/Documents/workspace/digifinex/mm_arb/client_test.py:5>> <Task pending coro=<exec() running at /Users/liujian/Documents/workspace/digifinex/mm_arb/client_test.py:5>>
1579175986.753356
本次执行时间为 2s,因此确定为并行执行,为何之前的源码没有并行,因为 python 的 async 返回的 coroutine object 并不会立即执行,只有在 asyncio.create_task(exec()) 创建成 Task 时才立即执行,这与 node.js 的 async 返回的 Promise 是立即执行不太一样,这就是这两个语言的 async/await 使用差异。
网友评论