Note
Refer [Threading vs Multiprocessing vs Asyncio]python3-threading-vs-multiprocessing-vs-asyncio
Asyncio is more lightweight than thread and suited for IO bound tasks, utilize single core only (concurrent but not parallel execution)
Multiple Process
import asyncioasync def run(name): for i in range(10): print(f"{name}", end='', flush=True) await asyncio.sleep(0.5) print(f"{name}[END]", end='', flush=True)async def main(): tasks = [run('a'), run('b'), run('c')] # wait for all task to finish await asyncio.gather(*tasks)asyncio.run(main())print('[STOP]')
abcabcabcabcabcabcabcabcabcabca[END]b[END]c[END][STOP]
Add Tasks Dynamically
- Launch new tasks dynamically (one by one over time)
- Quit when all tasks finished
import asyncioasync def run(name): for i in range(10): print(f"{name}", end='', flush=True) await asyncio.sleep(0.2) print(f"{name}[END]", end='', flush=True)async def main(): tasks = [] task_names = ['a', 'b', 'c'] while True: try: name = task_names.pop(0) if name: task = asyncio.create_task(run(name)) tasks.append(task) except IndexError: pass done, pending = await asyncio.wait(tasks, timeout=1) for _task in done: # sometimes fake done, forever wait block # await _task if _task.done(): # need this to show exception try: print('result', _task.result()) except Exception as e: print(e) if not pending: break print('main[END]', end='', flush=True)asyncio.run(main())print('[STOP]')
Shared Value
Since asyncio
run on single Thread/CPU concurrently (not in parallel), it is safe to share value.
Increment a counter value. Using array or class object as mutable type; if you pass in integer (immutable type), it will just be a local value of each coroutines).
import asyncioasync def run(name, count): for i in range(10): await asyncio.sleep(0.5) count[0] += 1 print(f"{name}[{count[0]}]", end='', flush=True) print(f"{name}[END]", end='', flush=True)async def main(): count = [0] tasks = [run('a', count), run('b', count), run('c', count)] # wait for all task to finish await asyncio.gather(*tasks)asyncio.run(main())print('[STOP]')
a[1]b[2]c[3]a[4]b[5]c[6]a[7]b[8]c[9]a[10]b[11]c[12]a[13]b[14]c[15]a[16]b[17]c[18]a[19]b[20]c[21]a[22]b[23]c[24]a[25]b[26]c[27]a[28]a[END]b[29]b[END]c[30]c[END][STOP]