如何让两个Asyncio异步函数并行运行?闹钟响时可进行数学问答
Python异步函数并行实现方案
要让alarm_logic和math_asking并行运行,核心是利用asyncio的任务机制,同时确保函数内部的等待操作不会阻塞事件循环。以下是完整的实现代码和关键说明:
完整代码示例
import asyncio import random from datetime import datetime async def alarm_logic(): # 模拟获取闹钟时间(这里设为当前时间+3秒,方便测试) alarm_time = datetime.now().timestamp() + 3 print(f"闹钟已设置,将在{datetime.fromtimestamp(alarm_time).strftime('%H:%M:%S')}响铃") # 循环等待,每次异步等待1秒,不阻塞事件循环 while datetime.now().timestamp() < alarm_time: await asyncio.sleep(1) # 到达时间后播放铃声 print("=== 闹钟响铃 ===") # 这里可以替换为实际播放铃声的代码 async def math_asking(): target_num = random.randint(1, 10) print("猜数字游戏开始:我想了一个1-10之间的数字,来猜猜看!") while True: # 异步处理同步输入,避免阻塞事件循环 user_input = await asyncio.to_thread(input, "请输入数字:") try: guess = int(user_input) if guess == target_num: print(f"猜对了!数字就是{target_num}") break elif guess < target_num: print("太小了,再试试!") else: print("太大了,再试试!") except ValueError: print("请输入有效的整数!") async def main(): # 创建两个并行异步任务 alarm_task = asyncio.create_task(alarm_logic()) math_task = asyncio.create_task(math_asking()) # 等待两个任务全部完成 await asyncio.gather(alarm_task, math_task) if __name__ == "__main__": asyncio.run(main())
关键注意事项
- 替换同步等待为异步等待:
alarm_logic里的循环等待必须用await asyncio.sleep(1),不能用time.sleep(1)——后者会直接阻塞整个事件循环,导致math_asking无法响应用户输入。 - 必须同时创建两个任务:只创建
alarm_logic的任务没用,得把math_asking也包装成任务加入事件循环,两者才能真正并行执行。 - 异步处理用户输入:
input()是同步阻塞函数,用asyncio.to_thread()把它放到单独线程执行,既能获取输入,又不会阻塞闹钟的等待逻辑。
内容的提问来源于stack exchange,提问作者Nikita Suslov
相关产品推荐
相关产品推荐

