ブロッキング/ノンブロッキング¶
ブロッキング¶
処理が終了するまで待つ
待っている間はほかの処理を行えない
time.sleep はブロッキングするので、完了を待ってから次の処理に移る
1import asyncio
2import time
3
4
5async def neru(n):
6 time.sleep(n)
7
8
9async def main():
10 await asyncio.create_task(neru(2))
11 await asyncio.create_task(neru(5))
12
13
14start = time.time()
15asyncio.run(main(), debug=True)
16print(f"time: {time.time() - start}")
実行結果: time: 7.009732246398926
ノンブロッキング¶
ブロッキングされない
ほかの処理ができる
asyncio.sleep はノンブロッキング処理なので、待っている間に次の処理に移れる
1import asyncio
2import time
3
4
5async def main():
6 await asyncio.create_task(asyncio.sleep(2))
7 await asyncio.create_task(asyncio.sleep(5))
8
9
10start = time.time()
11asyncio.run(main())
12print(f"time: {time.time() - start}")
実行結果: time: 5.004534006118774
ノンブロッキング関数の実装¶
Executor は非同期呼び出しをするためのクラス
1import asyncio
2import time
3
4
5async def neru(n):
6 loop = asyncio.get_running_loop()
7 loop.run_in_executor(None, time.sleep, n)
8
9
10async def main():
11 await asyncio.create_task(neru(3))
12 await asyncio.create_task(neru(5))
13
14
15start = time.time()
16asyncio.run(main())
17print(f"time: {time.time() - start}")
実行結果: time: 5.005532503128052
練習問題¶
次のコードを非同期(ノンブロッキング)に実装してください
1import time
2import urllib.request
3
4
5def _get_status_code(url):
6 with urllib.request.urlopen(url) as res:
7 return res.status
8
9
10def get_status_code(cor_name, n):
11 url = f"https://httpbin.org/delay/{n}"
12 http_status = _get_status_code(url)
13 print(f"{cor_name}: {http_status}")
14
15
16def main():
17 get_status_code("cor1", 2)
18 get_status_code("cor2", 5)
19
20
21start = time.time()
22main()
23print(f"time: {time.time() - start}")