Django如何使用asyncio协程和ThreadPoolExecutor多线程


Posted in Python onOctober 12, 2020

Django视图函数执行,不在主线程中,直接loop = asyncio.new_event_loop()
# 不能loop = asyncio.get_event_loop() 会触发RuntimeError: There is no current event loop in thread

因为asyncio程序中的每个线程都有自己的事件循环,但它只会在主线程中为你自动创建一个事件循环。所以如果你asyncio.get_event_loop在主线程中调用一次,它将自动创建一个循环对象并将其设置为默认值,但是如果你在一个子线程中再次调用它,你会得到这个错误。相反,您需要在线程启动时显式创建/设置事件循环:

loop = asyncio.new_event_loop()
asyncio.set_event_loop(loop)

在Django单个视图中使用asyncio实例代码如下(有多个IO任务时)

from django.views import View
import asyncio
import time
from django.http import JsonResponse
 
 
class TestAsyncioView(View):
  def get(self, request, *args, **kwargs):
    """
    利用asyncio和async await关键字(python3.5之前使用yield)实现协程
    """
    self.id = 5
    start_time = time.time()
 
    '''
    # 同步执行
    # results = [self.io_task1(self.id),
    # self.io_task2(self.id),
    # self.io_task2(self.id)]
    '''
 
 
    loop = asyncio.new_event_loop() # 或 loop = asyncio.SelectorEventLoop()
    asyncio.set_event_loop(loop)
    self.loop = loop
 
    works = [
      asyncio.ensure_future(self.io_task3(5)),
      asyncio.ensure_future(self.io_task3(5)),
      asyncio.ensure_future(self.io_task3(5)),
      asyncio.ensure_future(self.io_task3(5)),
      asyncio.ensure_future(self.io_task3(5)),
 
    ]
 
    try:
 
      results = loop.run_until_complete(asyncio.gather(*works)) # 两种写法
      # results = loop.run_until_complete(self.gather_tasks())
    finally:
      loop.close()
    end_time = time.time()
    return JsonResponse({'results': results, 'cost_time': (end_time - start_time)})
 
  async def gather_tasks(self):
 
    tasks = (
      self.make_future(self.io_task1, self.id),
      self.make_future(self.io_task2, self.id),
      self.make_future(self.io_task2, self.id),
      self.make_future(self.io_task1, self.id),
      self.make_future(self.io_task2, self.id),
      self.make_future(self.io_task2, self.id),
    )
    results = await asyncio.gather(*tasks)
    return results
 
  async def make_future(self, func, *args):
    future = self.loop.run_in_executor(None, func, *args)
    response = await future
    return response
 
  def io_task1(self, sleep_time):
    time.sleep(sleep_time)
    return 66
 
  def io_task2(self, sleep_time):
    time.sleep(sleep_time)
    return 77
 
  async def io_task3(self, sleep_time):
    # await asyncio.sleep(sleep_time)
    s = await self.do(sleep_time)
    return s
 
  async def do(self, sleep_time):
    await asyncio.sleep(sleep_time)
    return 66

在Django单个视图中使用ThreadPoolExecutor实例代码如下(有多个IO任务时)

from django.views import View
import time
from concurrent.futures import ThreadPoolExecutor, as_completed
 
 
class TestThreadView(View):
  def get(self, request, *args, **kargs):
    start_time = time.time()
    future_set = set()
    tasks = (self.io_task1, self.io_task2, self.io_task2, self.io_task1, self.io_task2, self.io_task2)
    with ThreadPoolExecutor(len(tasks)) as executor:
      for task in tasks:
        future = executor.submit(task, 5)
        future_set.add(future)
    for future in as_completed(future_set):
      error = future.exception()
      if error is not None:
        raise error
    results = self.get_results(future_set)
    end_time = time.time()
    return JsonResponse({'results': results, 'cost_time': (end_time - start_time)})
 
  def get_results(self, future_set):
 
    results = []
    for future in future_set:
      results.append(future.result())
    return results
 
  def io_task1(self, sleep_time):
    time.sleep(sleep_time)
    return 66
 
  def io_task2(self, sleep_time):
    time.sleep(sleep_time)
    return 77

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Python 相关文章推荐
python中常用的各种数据库操作模块和连接实例
May 29 Python
在Python中使用base64模块处理字符编码的教程
Apr 28 Python
编写Python脚本批量下载DesktopNexus壁纸的教程
May 06 Python
以windows service方式运行Python程序的方法
Jun 03 Python
Matplotlib中文乱码的3种解决方案
Nov 15 Python
django自定义模板标签过程解析
Dec 14 Python
python3下pygame如何实现显示中文
Jan 11 Python
Python面向对象程序设计之类和对象、实例变量、类变量用法分析
Mar 23 Python
TensorFlow tf.nn.conv2d_transpose是怎样实现反卷积的
Apr 20 Python
在django中form的label和verbose name的区别说明
May 20 Python
python 实现性别识别
Nov 21 Python
Python实现双向链表基本操作
May 25 Python
使用Python中tkinter库简单gui界面制作及打包成exe的操作方法(二)
Oct 12 #Python
使用Python将xmind脑图转成excel用例的实现代码(一)
Oct 12 #Python
使用python把xmind转换成excel测试用例的实现代码
Oct 12 #Python
Python Sqlalchemy如何实现select for update
Oct 12 #Python
浅析PyCharm 的初始设置(知道)
Oct 12 #Python
Pandas替换及部分替换(replace)实现流程详解
Oct 12 #Python
Django windows使用Apache实现部署流程解析
Oct 12 #Python
You might like
PHP字符过滤函数去除字符串最后一个逗号(rtrim)
2013/03/26 PHP
Zend的MVC机制使用分析(一)
2013/05/02 PHP
php源码分析之DZX1.5加密解密函数authcode用法
2015/06/17 PHP
PHP + plupload.js实现多图上传并显示进度条加删除实例代码
2017/03/06 PHP
PHP利用递归函数实现无限级分类的方法
2019/03/22 PHP
Yii框架学习笔记之session与cookie简单操作示例
2019/04/30 PHP
IE DOM实现存在的部分问题及解决方法
2009/07/25 Javascript
用js实现判断当前网址的来路如果不是指定的来路就跳转到指定页面
2011/05/02 Javascript
基于jQuery的图片剪切插件
2011/08/03 Javascript
基于jquery编写的横向自适应幻灯片切换特效的实例代码
2013/08/06 Javascript
js+css实现有立体感的按钮式文字竖排菜单效果
2015/09/01 Javascript
jQuery横向擦除焦点图特效代码分享
2015/09/06 Javascript
jQuery获取table下某一行某一列的值实现代码
2017/04/07 jQuery
初识NodeJS服务端开发入门(Express+MySQL)
2017/04/07 NodeJs
ReactNative中使用Redux架构总结
2017/12/15 Javascript
解决elementUI 切换tab后 el_table 固定列下方多了一条线问题
2020/07/19 Javascript
js实现批量删除功能
2020/08/27 Javascript
[52:08]DOTA2上海特级锦标赛主赛事日 - 3 败者组第三轮#2Fnatic VS OG第一局
2016/03/05 DOTA
Python编程实现的简单神经网络算法示例
2018/01/26 Python
python实现俄罗斯方块游戏
2020/03/25 Python
对Python使用mfcc的两种方式详解
2019/01/09 Python
python单向循环链表原理与实现方法示例
2019/12/03 Python
pytorch 实现模型不同层设置不同的学习率方式
2020/01/06 Python
Python selenium 加载并保存QQ群成员,去除其群主、管理员信息的示例代码
2020/05/28 Python
Keras预训练的ImageNet模型实现分类操作
2020/07/07 Python
python基于socket模拟实现ssh远程执行命令
2020/12/05 Python
HTML5 Canvas自定义圆角矩形与虚线示例代码
2013/08/02 HTML / CSS
英语专业学子个人的自我评价
2013/10/02 职场文书
《草原》教学反思
2014/02/15 职场文书
小学安全教育材料
2014/02/17 职场文书
《桂花雨》教学反思
2014/04/12 职场文书
《青山处处埋忠骨》教学反思
2014/04/22 职场文书
教师学习群众路线心得体会
2014/11/04 职场文书
2015年教师见习期工作总结
2015/05/20 职场文书
《雪域豹影》读后感:父爱的伟大
2019/12/23 职场文书
压缩Redis里的字符串大对象操作
2021/06/23 Redis