django_orm查询性能优化方法


Posted in Python onAugust 20, 2018

查询操作和性能优化

1.基本操作

models.Tb1.objects.create(c1='xx', c2='oo') 增加一条数据,可以接受字典类型数据 **kwargs
 
obj = models.Tb1(c1='xx', c2='oo')
obj.save()

models.Tb1.objects.get(id=123)     # 获取单条数据,不存在则报错(不建议)
models.Tb1.objects.all()        # 获取全部
models.Tb1.objects.filter(name='seven') # 获取指定条件的数据
models.Tb1.objects.exclude(name='seven') # 获取指定条件的数据


models.Tb1.objects.filter(name='seven').delete() # 删除指定条件的数据


models.Tb1.objects.filter(name='seven').update(gender='0') # 将指定条件的数据更新,均支持 **kwargs
obj = models.Tb1.objects.get(id=1)
obj.c1 = '111'
obj.save()                         # 修改单条数据

2.Foreign key的使用原因

  • 约束
  • 节省硬盘

但是多表查询会降低速度,大型程序反而不使用外键,而是用单表(约束的时候,通过代码判断)

extra

extra(self, select=None, where=None, params=None, tables=None, order_by=None, select_params=None)
  Entry.objects.extra(select={'new_id': "select col from sometable where othercol > %s"}, select_params=(1,))
  Entry.objects.extra(where=['headline=%s'], params=['Lennon'])
  Entry.objects.extra(where=["foo='a' OR bar = 'a'", "baz = 'a'"])
  Entry.objects.extra(select={'new_id': "select id from tb where id > %s"}, select_params=(1,), order_by=['-nid'])

F查询

from django.db.models import F
  models.Tb1.objects.update(num=F('num')+1)

Q查询

方式一:

Q(nid__gt=10)
  Q(nid=8) | Q(nid__gt=10)
  Q(Q(nid=8) | Q(nid__gt=10)) & Q(caption='root')

方式二:
 

con = Q()
  q1 = Q()
  q1.connector = 'OR'
  q1.children.append(('id', 1))
  q1.children.append(('id', 10))
  q1.children.append(('id', 9))
  q2 = Q()
  q2.connector = 'OR'
  q2.children.append(('c1', 1))
  q2.children.append(('c1', 10))
  q2.children.append(('c1', 9))
  con.add(q1, 'AND')
  con.add(q2, 'AND')
 
  models.Tb1.objects.filter(con)

exclude(self, *args, **kwargs)

# 条件查询
 # 条件可以是:参数,字典,Q

select_related(self, *fields)

性能相关:表之间进行join连表操作,一次性获取关联的数据。

model.tb.objects.all().select_related()
  model.tb.objects.all().select_related('外键字段')
  model.tb.objects.all().select_related('外键字段__外键字段')

prefetch_related(self, *lookups)

性能相关:多表连表操作时速度会慢,使用其执行多次SQL查询  在内存中做关联,而不会再做连表查询

# 第一次 获取所有用户表
# 第二次 获取用户类型表where id in (用户表中的查到的所有用户ID)
models.UserInfo.objects.prefetch_related('外键字段')

annotate(self, *args, **kwargs)

# 用于实现聚合group by查询
from django.db.models import Count, Avg, Max, Min, Sum
 v = models.UserInfo.objects.values('u_id').annotate(uid=Count('u_id'))
# SELECT u_id, COUNT(ui) AS `uid` FROM UserInfo GROUP BY u_id
v = models.UserInfo.objects.values('u_id').annotate(uid=Count('u_id')).filter(uid__gt=1)
# SELECT u_id, COUNT(ui_id) AS `uid` FROM UserInfo GROUP BY u_id having count(u_id) > 1
v = models.UserInfo.objects.values('u_id').annotate(uid=Count('u_id',distinct=True)).filter(uid__gt=1)
# SELECT u_id, COUNT( DISTINCT ui_id) AS `uid` FROM UserInfo GROUP BY u_id having count(u_id) > 1

extra(self, select=None, where=None, params=None, tables=None, order_by=None, select_params=None)

# 构造额外的查询条件或者映射,如:子查询
Entry.objects.extra(select={'new_id': "select col from sometable where othercol > %s"}, select_params=(1,))
Entry.objects.extra(where=['headline=%s'], params=['Lennon'])
Entry.objects.extra(where=["foo='a' OR bar = 'a'", "baz = 'a'"])
Entry.objects.extra(select={'new_id': "select id from tb where id > %s"}, select_params=(1,), order_by=['-nid'])

reverse(self):

# 倒序
 models.UserInfo.objects.all().order_by('-nid').reverse()
# 注:如果存在order_by,reverse则是倒序,如果多个排序则一一倒序

下面两个 取到的是对象,并且注意 取到的对象可以 获取其他字段(这样会再去查找该字段降低性能

defer(self, *fields):

models.UserInfo.objects.defer('username','id')
或
models.UserInfo.objects.filter(...).defer('username','id')
# 映射中排除某列数据

only(self, *fields):

# 仅取某个表中的数据
models.UserInfo.objects.only('username','id')
或
models.UserInfo.objects.filter(...).only('username','id')

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

Python 相关文章推荐
Python中pygame安装方法图文详解
Nov 11 Python
Python利用splinter实现浏览器自动化操作方法
May 11 Python
利用pyecharts实现地图可视化的例子
Aug 12 Python
阿里云ECS服务器部署django的方法
Aug 29 Python
Django 限制访问频率的思路详解
Dec 24 Python
Python使用os.listdir和os.walk获取文件路径
May 21 Python
浅谈Keras的Sequential与PyTorch的Sequential的区别
Jun 17 Python
Tensorflow与Keras自适应使用显存方式
Jun 22 Python
Django Form设置文本框为readonly操作
Jul 03 Python
Python3安装模块报错Microsoft Visual C++ 14.0 is required的解决方法
Jul 28 Python
python代数式括号有效性检验示例代码
Oct 04 Python
Python利用imshow制作自定义渐变填充柱状图(colorbar)
Dec 10 Python
Python Requests库基本用法示例
Aug 20 #Python
Django中使用第三方登录的示例代码
Aug 20 #Python
基于Django框架利用Ajax实现点赞功能实例代码
Aug 19 #Python
分析python请求数据
Aug 19 #Python
浅谈django orm 优化
Aug 18 #Python
django连接mysql配置方法总结(推荐)
Aug 18 #Python
python画一个玫瑰和一个爱心
Aug 18 #Python
You might like
php巧获服务器端信息
2006/12/06 PHP
PHP单例模式模拟Java Bean实现方法示例
2018/12/07 PHP
PHP从零开始打造自己的MVC框架之入口文件实现方法详解
2019/06/03 PHP
ThinkPHP5与单元测试PHPUnit使用详解
2020/02/23 PHP
for 循环性能比较 提高for循环的效率
2009/03/19 Javascript
基于jQuery的倒计时实现代码
2012/05/30 Javascript
js 延迟加载 改变JS的位置加快网页加载速度
2012/12/11 Javascript
设为首页和收藏的Javascript代码(亲测兼容IE,Firefox,chrome等浏览器)
2013/11/18 Javascript
javaScript中Math()函数注意事项
2015/06/18 Javascript
jquery+ajax实现注册实时验证实例详解
2015/12/08 Javascript
jQuery控制frames及frame页面JS的方法
2016/03/08 Javascript
Boostrap实现的登录界面实例代码
2016/10/09 Javascript
jquery延迟对象解析
2016/10/26 Javascript
简单谈谈ES6的六个小特性
2016/11/18 Javascript
vue 中自定义指令改变data中的值
2017/06/02 Javascript
vue的事件绑定与方法详解
2017/08/16 Javascript
浅析node.js的模块加载机制
2018/05/25 Javascript
使用vue-router在Vue页面之间传递数据的方法
2019/07/15 Javascript
JavaScript基于面向对象实现的无缝滚动轮播示例
2020/01/17 Javascript
Python整型运算之布尔型、标准整型、长整型操作示例
2017/07/21 Python
django 通过ajax完成邮箱用户注册、激活账号的方法
2018/04/17 Python
Django处理文件上传File Uploads的实例
2018/05/28 Python
python实现对任意大小图片均匀切割的示例
2018/12/05 Python
详解DeBug Python神级工具PySnooper
2019/07/03 Python
PyCharm2018 安装及破解方法实现步骤
2019/09/09 Python
pytorch的梯度计算以及backward方法详解
2020/01/10 Python
使用python无账号无限制获取企查查信息的实例代码
2020/04/17 Python
keras读取h5文件load_weights、load代码操作
2020/06/12 Python
Python sklearn中的.fit与.predict的用法说明
2020/06/28 Python
CSS3轻松实现清新 Loading 效果的简单实例
2016/06/06 HTML / CSS
路由表示做什么用的?在linux环境中怎么来配置一条默认路由?
2013/06/07 面试题
学校后勤人员职责
2013/12/27 职场文书
关于元旦的广播稿
2014/02/16 职场文书
项目建议书格式
2014/03/12 职场文书
2019最新版股权转让及委托持股协议书范本
2019/08/07 职场文书
一次Mysql update sql不当引起的生产故障记录
2022/04/01 MySQL