Django 系列博客(十二)
Django 系列博客(十二)
前言
本篇博客继续介绍 Django 中的查询,分别为聚合查询和分组查询,以及 F 和 Q 查询。
聚合查询
语法:aggregate(*args, **kwargs)
# 计算所有图书的平均价格
from django.db.models import Avg
Book.objects.all().aggregate(Avg('price'))
aggregate()是 QuerySet 的一个终止子句,意思是说,它返回一个包含一些键值对的字典。键的名称是聚合值得标识符,值是计算出来的聚合值。建的名称是按照字段和聚合函数的名称自动生成出来的。如果你想要为聚合值指定个名称,可以向聚合子句提供它。
Book.objects.aggregate(average_price=Avg('price'))
如果你希望生成不止一个聚合值,你可以向 aggregate()子句中添加另一个参数。所以如果想知道所有图书价格的最大值和最小值,可以这样查询:
from django.db.models import Avg, Max, Min
Book.objects.aggregate(Avg('price'), Max('price'), Min('price'))
具体例子:
# 查询所有书籍的平均价格
from django.db.models import Avg,Count,Max,Min
ret=Book.objects.all().aggregate(Avg('price'))
# {'price__avg': 202.896}
# 可以改名字
ret=Book.objects.all().aggregate(avg_price=Avg('price'))
# 统计平均价格和最大价格
ret=Book.objects.all().aggregate(avg_price=Avg('price'),max_price=Max('price'))
# 统计最小价格
ret = Book.objects.all().aggregate(avg_price=Avg('price'), min_price=Min('price'))
# 统计个数和平均价格
ret = Book.objects.all().aggregate(avg_price=Avg('price'), max_price=Max('price'),count=Count('price'))
ret = Book.objects.all().aggregate(avg_price=Avg('price'), max_price=Max('price'),count=Count('nid'))
print(ret)
分组查询
总结:
group by 那个表就以那个表作为基表
values 在前:表示 group by
values 在后:表示取值
filter 在前:表示 where 条件
filter 在后:表示 having
分组查询案例
# 查询所有作者写的书的总价格大于26的
# filter()在annotate后面,表示对分组后的结果进行筛选,相当于having
# annotate前的values()表示按该字段分组,相当于group by,可以省略,默认会按Author的id分组
# 后面的values()表示取值
ret=Author.objects.all().values('pk').annotate(s=Sum('book__price')).filter(s__gt=26).values('name','s')
等价于
ret=Author.objects.all().annotate(s=Sum('book__price')).filter(s__gt=26).values('name','s')
# 查询各个作者出的书的总价格
# s相当于给求和结果取名字,在vlaues取值中,可以引用
ret = Author.objects.all().annotate(s=Sum('price')).values('name','s')
print(ret)
# 统计不止一个作者的图书
ret=Book.objects.all().values('pk').annotate(c=Count('authors')).filter(c__gt=1).values('name','c')
print(ret)
等价于
ret = Book.objects.annotate(author_num=Count("authors")).filter(author_num__gt=1).values('name','author_num')
print(ret)
F 查询
什么是 F 查询
如果要对两个字段的值作比较,就不能直接比较,必须借助 F()的实例,可以在查询中引用字段,来比较同一个 model 实例中两个不同字段的值。
语法
from django.db.models import F
fliter(commit_num_gt=F('read_num'))
F 查询的使用
# 查询评论数大于阅读数的书
book = models.Book.objects.filter(commit_num__gt=F('read_num')).values('name')
# 把所有书的评论数加1
models.Book.objects.all().update(commit_num=F('commit_num')+1)
Q 查询
什么是 Q 查询
对两个字段的值进行或、与、非运算,不能直接运算,需要用 Q()的实例。
语法
# 且 -----> &
# 或 -----> |
# 非 -----> ~
from django.db.models import Q
fliter(Q(name='tom')|Q(name='tony'))
Q 查询的使用
# 查询不是tom写的书的名字
ret = models.Book.objects.filter(~Q(authors__name='tom')).values('name')
# 查询作者名字是tom或者名字是tony的书
ret = models.Book.objects.filter(Q(authors__name='tom')|Q(authors__name='tony')).values('name')
补充:
在实际开发中,外键通常不用:
约束性太强
查询效率低
可以通过
db_constraint=False来取消外键约束,在 orm 创建表的时候,外键的约束不会存在,但是这样会产生脏数据。建外键约束,包括 unique 都是为了不产生脏数据。
Django 系列博客(十二)的更多相关文章
- Django 系列博客(二)
Django 系列博客(二) 前言 今天博客的内容为使用 Django 完成第一个 Django 页面,并进行一些简单页面的搭建和转跳. 命令行搭建 Django 项目 创建纯净虚拟环境 在上一篇博客 ...
- Django 系列博客(十六)
Django 系列博客(十六) 前言 本篇博客介绍 Django 的 forms 组件. 基本属性介绍 创建 forms 类时,主要涉及到字段和插件,字段用于对用户请求数据的验证,插件用于自动生成 h ...
- Django 系列博客(十)
Django 系列博客(十) 前言 本篇博客介绍在 Django 中如何对数据库进行增删查改,主要为对单表进行操作. ORM简介 查询数据层次图解:如果操作 mysql,ORM 是在 pymysql ...
- Django 系列博客(十四)
Django 系列博客(十四) 前言 本篇博客介绍在 html 中使用 ajax 与后台进行数据交互. 什么是 ajax ajax(Asynchronous Javascript And XML)翻译 ...
- Django 系列博客(十三)
Django 系列博客(十三) 前言 本篇博客介绍 Django 中的常用字段和参数. ORM 字段 AutoField int 自增列,必须填入参数 primary_key=True.当 model ...
- Django 系列博客(十一)
Django 系列博客(十一) 前言 本篇博客介绍使用 ORM 来进行多表的操作,当然重点在查询方面. 创建表 实例: 作者模型:一个作者有姓名和年龄. 作者详细模型:把作者的详情放到详情表,包含生日 ...
- Django 系列博客(六)
Django 系列博客(六) 前言 本篇博客介绍 Django 中的路由控制部分,一个网络请求首先到达的就是路由这部分,经过路由与视图层的映射关系再执行相应的代码逻辑并将结果返回给客户端. Djang ...
- Django 系列博客(九)
Django 系列博客(九) 前言 本篇博客介绍 Django 模板的导入与继承以及导入导入静态文件的几种方式. 模板导入 模板导入 语法:``{% include '模板名称' %} 如下: < ...
- Django 系列博客(八)
Django 系列博客(八) 前言 本篇博客介绍 Django 中的模板层,模板都是Django 使用相关函数渲染后传输给前端在显式的,为了想要渲染出我们想要的数据,需要学习模板语法,相关过滤器.标签 ...
随机推荐
- sublime设置sublimeREPL-python-run current file 快捷键
弄了3个小时的快捷键,一直不能成功使用,百度上一堆一样的方法,最后FQ才找到能用的方法,真是服了. 方法: ①首选项->快捷键设置 填写如下内容: [ {"keys": [& ...
- 初入linux系统
作为微软的老铁粉了,看到微软进军linux这么久了,是时候该跟上脚本了,不然该落后了,脚步是如此之快,着实让我吃了一惊,说干就干, 绝不是开玩笑的,谁也阻止不了.net开源,跨平台的脚步了.以前别人说 ...
- iOS UILabel 文字 置顶/置底 实现
iOS UILabel控件默认文字位置是居中的,如图所示: 但是我们经常碰到这样的需求,希望文字向上置顶,或者向下置底,但是很遗憾,iOS API中并没有提供相应的属性和方法,需要我们手动设置. 利用 ...
- C++ 初步
c++新特性: 1. 初始化方法: 复制初始化 int x=1024; 直接初始化 int x (1024); 2.变量随用随定义 3.增加bool数据类型 输入输出: cout<<x; ...
- [LeetCode] Hand of Straights 一手顺子牌
Alice has a hand of cards, given as an array of integers. Now she wants to rearrange the cards into ...
- VS2017Release+x64失败,LNK1104,无法打开文件"msvcprt.lib"
采用VS2017+Qt5.10联合开发环境建立开发,将Qt的库包含到VS中使用VS2017的Debug+x64模式调试程序,通过并出现对应的EXE应用程序! 但是转换到Release+x64模式出现问 ...
- 发布版本Debug和Release的区别
1.Debug是调试版本不会对项目发布的内容进行优化,并且包含调试信息容量会大很多 2.Release不对源代码进行调试,对应用程序的速度进行优化,使得发布的内容容量等都是最优的
- Linux 系统中的内部与外部命令
linux中的命令大致可分为两类,内部命令和外部命令: 内部命令(builtin command):也称shell内嵌命令 外部命令(external command):存放在一个文件中,使用时需要去 ...
- 解决用友U8删除用户时提示“用户已启用”不能删除的问题
USE UFSystem go DECLARE @cUser_Id NVARCHAR(20) SET @cUser_Id='用户的登录名' DELETE l FROM dbo.UA_TaskLog l ...
- 请不要在JDK7及以上用Json-lib了
[Json-lib 介绍] Json-lib 是以前 Java 常用的一个 Json 库,最后的版本是 2.4,分别提供了 JDK 1.3 和 1.5 的支持,最后更新时间是 2010年12月14日. ...