中文商城html网站模板,网站 设计 深圳,长沙seo推广公司,网站县区分站点建设同步等待异步协同程序如果一个异步事件循环已经通过调用loop.run_forever运行#xff0c;它将阻塞执行线程#xff0c;直到loop.stop被调用[请参阅docs]。因此#xff0c;同步等待的唯一方法是在一个专用线程上运行事件循环#xff0c;在循环上调度异步函数#xff0c;然后…同步等待异步协同程序如果一个异步事件循环已经通过调用loop.run_forever运行它将阻塞执行线程直到loop.stop被调用[请参阅docs]。因此同步等待的唯一方法是在一个专用线程上运行事件循环在循环上调度异步函数然后从另一个线程同步地等待它。在为此我按照用户4815162342的answer编写了自己的最小解决方案。我还添加了在所有工作完成后清理循环的部分[参见^{}]。在下面代码中的main函数在一个专用线程上运行事件循环调度事件循环上的多个任务以及同步等待结果的任务。同步等待将阻塞直到所需的结果准备就绪。最后循环被关闭并优雅地与其线程一起清理。在专用线程和函数stop_loop、run_forever_safe、和{}可以封装在模块或类中。在有关线程安全的注意事项请参阅asyncio docs中的“Concurrency and Multithreading”部分。在import asyncioimport threading#def stop_loop(loop): stops an event loop loop.stop()print (.: LOOP STOPPED:, loop.is_running())def run_forever_safe(loop): run a loop for ever and clean up after being stopped loop.run_forever()# NOTE: loop.run_forever returns after calling loop.stop# cancell all tasks and close the loop gracefullyprint(.: CLOSING LOOP...)# source: loop_tasks_all asyncio.Task.all_tasks(looploop)for task in loop_tasks_all: task.cancel()# NOTE: cancel does not guarantee that the Task will be cancelledfor task in loop_tasks_all:if not (task.done() or task.cancelled()):try:# wait for task cancellationsloop.run_until_complete(task)except asyncio.CancelledError: pass#END forprint(.: ALL TASKS CANCELLED.)loop.close()print(.: LOOP CLOSED:, loop.is_closed())def await_sync(task): synchronously waits for a task while not task.done(): passprint(.: AWAITED TASK DONE)return task.result()#async def asyncTask(loop, k): asynchronous task print( start async task %s % k)await asyncio.sleep(3, looploop)print( end async task %s. % k)key KEY#%s % kreturn keydef main():loop asyncio.new_event_loop() # construct a new event loop# closures for running and stopping the event-looprun_loop_forever lambda: run_forever_safe(loop)close_loop_safe lambda: loop.call_soon_threadsafe(stop_loop, loop)# make dedicated thread for running the event loopthread threading.Thread(targetrun_loop_forever)# add some tasks along with my particular taskmyTask asyncio.run_coroutine_threadsafe(asyncTask(loop, 100200300), looploop)otherTasks [asyncio.run_coroutine_threadsafe(asyncTask(loop, i), looploop)for i in range(1, 10)]# begin the thread to run the event-loopprint(.: EVENT-LOOP THREAD START)thread.start()# _synchronously_ wait for the result of my taskresult await_sync(myTask) # blocks until task is doneprint(* final result of my task:, result)#... do lots of work ...print(*** ALL WORK DONE ***)## close the loop gracefully when everything is finishedclose_loop_safe()thread.join()#main()