网络编程
位置:首页>> 网络编程>> Python编程>> Django分组聚合查询实例分享

Django分组聚合查询实例分享

作者:Afrafre  发布时间:2023-08-07 21:44:16 

标签:Django,分组聚合查询

多表查询

1. 增删改

一对多:先一后多,外键可以为对象或依赖表的主键(publish and book)


publish = Publish.objects.create()
Book.objects.create(....publish=publish|publish_id=publish.id)

删: 默认存在级联删除

改: book修改外键,外键一定存在

多对多:

关系表的获取(book(主键) and author) book.author

增:book.author.add(作者对象们|主键们)

删: clear()清除 remove() 可删除单个作者

改: set([作者对象们|主键们])

2. 查

基于对象,正向找属性,反向找类名小写,多条记录类名小写_set


book.publish.first().name (book 一定是对象,不是queryset)
publish.book_set.first().name

基于双下划线:


Book.objects.filter(id=1).values('publish__name')[0] (values 查出的也是queryset)
publish.values('book__name')

今日内容

1. 分组查询: 聚合结果 group_by()

2. 聚合函数

3. 字段

分组查询(单独聚合查询 and 分组聚合查询---基于mysql)

Book: id name price publish_date publish

聚合函数可以单独使用 ---- 整张表是一个大组

select max(price) from book

聚合函数在分组下使用


select max(price) as high_price from book group by publish having high_price > 50;

聚合查询---基于ORM

聚合函数的使用场景:

单独使用:不分组,只查聚合结果

分组使用: 按字段分组,可查分组字段与聚合结果

导入聚合函数:

from django.db.models import Avg,Max,Min,Count,Sum

单独聚合查询:aggregate (聚集,合集)---不分组

# 语法

# 聚合函数: Max, Min,Sum, Avg, Count

aggregate(别名=聚合函数('字段‘)

规则:

1. 可以同时对多个字段进行聚合处理: aggregate(name1= , name2= ...)

2. 是QuerySet 对象的方法(all,filter)

3. 返回值为dict类型

4. 在aggregate之前的values操作没作用,被忽略

例: 所有书中最贵的书的价格


dic = Book.objects.all().aggregate(high_price=max('price),low_price=min('price'))

分组聚合查询: annotate (注释,做注解) --- 分组

# 语法
values('分组字段').annotate(别名=聚合函数(‘字段').filter(聚合别名条件).values('取分组字段','取聚合字段别名'))

规则:

1. values --- annotate 分组组合, values控制分组的字段,annotate控制聚合字段

2. values 可以按多个字段分组values('字段1‘,'字段2‘)

3. 可以同时对多个字段进行聚合处理 annotate(别名1=max('price'),别名2=min('price'))

4. 分组后的filter 代表having判断,只对聚合字段进行条件判断,(参数为非聚合或分组进行条件判断代表where判断)

5. 取字段值 values() 省略默认取所有分组字段和聚合字段,也可以自己定义(对非分组或非聚合字段,该字段自动被变成分组字段)

# 案例:每个出版社出版的最贵的书的价格高于50元的出版社名与最高价格

# 思路:按出版社分组(从book出发),high_price=max('price'), filter(high_price__gt=50)

# 每个组的价格最贵的


Book.objects.all().values('publish__name').annotate(high_price=max('price').filter(high_price__gl=50).values('publish__name','high_price'))


字段属性

1. null: 默认Fasle(默认字段不能为空) , True 表示字段可为null
2. blank: 默认False, True 表示字段可以为空
3.choice: 限制了该选项字段值必须是指定的choice 中的一个 (元组套元组)
sex = models.SmallIntegerField(choice=((1,'man'),(2,'female')))
obj.get_sex_display()

有choices 这个字段的: 要取得'女‘或'男‘, get_字段名sex_display() --超出失效
4. db_column: 自定义字段名
db_column='gender' 起别名该sex
5. db_index : True 设置索引
6. default: 字段默认值
7. editable: 默认为True, False: 不在 admin 界面显示
8. primary_key : TRUE 为主键,
9. unique: true 字段值不可重复

字段

1. AutoField(): 默认自增主键(primary_key=True)
2. BooleanField(): 布尔字段, 对应database tinyint 类型
3. CharField(): 字符类型(默认不为空)
max_length=20,null=True 可以为空
4. DateField(): 年月日
auto_now = True 数据别更新就会更新时间
auto_now_add = True 数据第一次产生时
5. DateTimeField(): 年月日时分秒
auto_now = True 数据别更新就会更新时间
auto_now_add = True 数据第一次产生时
6. DecimalField(): 混合精度的小数类型
max_digits = 5, 含小数为的最大位数
decimal_places = 2 , 小数位数
7. IntegerField(): 整型

不常用字段

关系字段

1. ForeignKey(): 外键字段
to= 关联模型类 (一对多)
to_file = 关联字段,省略默认关联主键
on_delete (外键关联数据被删除时的操作)
models.CASCADE 级联删除
modles.PROTECT 抛出异常
models.SET_NULL 设置空值
modles.SET_DEFAULT 设置默认值
models.SET(value) 自定义值
related_name 自定义反向查询的字段名
db_constraint=False, 取消关联,但还可以使用链表查询
总结: models.ForeignKey(to='related class name', null=True,on_delete=models.SET_NULL,db_constraint=False,related_name='本类名小写')
2. OneToOneField(): 一对一字段
同外键
3, ManyToManyField() :多对多关系
to = 关联模型类
through=关联关系类
through_fields关联关系表中(本身字段,关联字段)

断开外键关联的ForeignKey使用(一对多,一对一)

# 一对多查询 ----(publish and book)
# 方式一 : 不使用外键,在book 中添加 publish_id 属性
# 不在支持Django ORM 链表查询语法

# class Book(models.Model):
# name = models.CharField(max_length=20)
# publish_id = models.IntegerField(null=True)
#
# class Publish(models.Model):
# name = models.CharField(max_length=20)
#
# # 查询方式:
# # 通过第一本书book 找出版社
# # id = Book.objects.first().publish_id
# # publish = Publish.objects.filter(id=id)[0].name
# # print(publish)

方式二:使用外键, 用db_constrain=False 字段段开连接
# 可以使用Django ORM连表查询语法
class Book(models.Model):
name = models.CharField(max_length=20)
publish = models.ForeignKey(to='Publish',db_constraint=False,null=True,on_delete=models.SET_NULL) # to_field='id' 不写会自动添加

class Publish(models.Model):
name = models.CharField(max_length=20)

# 书的出版社 (外键方式)
# print(Book.objects.first().publish.name)
# print(Book.objects.filter(pk=1).values('publish__name'))

断开关联--- 多对多自动创建关系表

# 断开关联(db_constraint属性)的多对多自动创建关系表 (book(外键) and author)
# 断开后依然支持Django ORMlianiao 查询语法
# 当新表中无需新加额外字段时, 可以自动创建
class MyBook(models.Model):
name = models.CharField(max_length=20)
# 这里会产生第三张表
book_author = models.ManyToManyField(to='MyAuthor',db_constraint=False)

class MyAuthor(models.Model):
name = models.CharField(max_length=20)


# # 查询方法
# # 多对多(自动创建第三张表): 书的作者
# b1 = MyBook.objects.first()
# # b1.book_author 这个是关系表
# for author in b1.book_author.all():
# print(author.name)

# print(MyBook.objects.filter(pk=1).values('book_author__name'))

断开关联 --- 多对多手动创建关系表

# 手动创建关系表的原因: 可以拥有自身字段,可以通过关系表类名直接获取第三张表

# 手动创建关系表可以让关系表可以拥有更多的自身的字段,同时通过关系表类名可以直接获取第三张表
'''
# ****
# 1、和自动建立关系表类似,依然支持Django ORM连表查询语法(多对多借助关系表连表查询)
class Book(models.Model):
name = models.CharField(max_length=20)

class Author(models.Model):
name = models.CharField(max_length=20)

class Book_Author(models.Model):
book = models.ForeignKey(to="Book", null=True, on_delete=models.SET_NULL, db_constraint=False)
author = models.ForeignKey(to='Author', null=True, on_delete=models.SET_NULL, db_constraint=False)
time = models.DateField()
'''

'''
# ****
2、手动创建关系表,在关系表中用ForeignKey方式支持基于外键关系表的ORM连表查询,同时明确ManyToManyField字段,所以也支持ORM正向方向连表查询
-- db_constraint=False断开关联可以在ForeignKey或ManyToManyField任意一方完成
class Book(models.Model):
name = models.CharField(max_length=20)
# 明确through与through_fields,ManyToManyField才不会自动建立关系表,没有关联关系后就不能再使用db_constraint字段属性
author = models.ManyToManyField(to='Author', through='Book_Author', through_fields=('book_id', 'author_id'))

class Author(models.Model):
name = models.CharField(max_length=20)

class Book_Author(models.Model):
book = models.ForeignKey(to="Book", null=True, on_delete=models.SET_NULL, db_constraint=False)
author = models.ForeignKey(to='Author', null=True, on_delete=models.SET_NULL, db_constraint=False)
time = models.DateField()
'''
# 总结:手动创建第三张表,第三张表的增删改就采用关系表类名衍生的create|delete|update,就不再拥有add|clear|remove|set(因为关系表拥有自己的字段,这些方法无法直接操作这些字段)

来源:https://www.cnblogs.com/Afrafre/p/12799202.html

0
投稿

猜你喜欢

  • 目前已经有很多生成html的新闻系统,但是都是用的模板,本函数实现把asp页面产生的html代码保存成为一个html文件,这样就没有必要改动
  • 内容摘要:我们在浏览一些文章的时候,当鼠标选中一些文字的时候,就出现了一些隐藏的字符,平常是看不到的。这些干扰码一般有两种,一是随机无意义的
  • 多版本并发控制Multiversion Concurrency Control大部分的MySQL的存储 引擎,比如InnoDB,Falcon
  • CSS入门很简单,规则不多,写法也比较灵活,因此也带来了很多有创意的写法。跟IE一样,很好的容错性,像《 边框样式写法总结 》所说的bord
  • 很多时候,我们都在说设计需要引导用户,尤其是在对初级用户的引导上,很大程度决定着产品能否快速聚拢用户的可能;但同样很多时候,用户并不需要引导
  • 小小程序猿SQL Server认知的成长 1.没毕业或工作没多久,只知道有数据库、SQL这么个东东,浑然分不清SQL和Sql Server
  • 这个功能现在很多网站,论坛都有,本站也有呵呵!如果您还不知道如何实现这个功能,没关系看看本文吧!我将给你介绍怎么给你的网站加上运行代码框的功
  • * 对子查询和Join进行了优化,包括对MyISAD和InnoB存储引擎分散范围内的批量索引访问。* 增加了 BACKUP DATABASE
  • 如果你想让你的IIS支持wml,做个wap网站,只需作小小的改变就行了.虽然目前支持wml的虚拟主机极少,但是自己在本机上玩玩也好的.首先在
  • 对于什么是好设计,一万个人那里至少有一万零一个答案。每个人都有自己的答案,有的人还不止一个答案。老师说,一定要在设计里灌注自己的思想,有了自
  • 实现在线人数统计最常用的方法就是golobal.asa结合session做,但这种方法有两个不利: 1、每个session要占用12k的服务
  • 另外他们列出的这些区别有些是蛮有意义的,有些可能由于他们本人的MySQL DBA的身份,对Oracle的理解有些偏差,有些则有凑数的嫌疑.
  • 很多人说设计是力求细节的,在网页设计里表达出的细节就是图标。图标在一个设计里带来了额外的注解并且使设计里的对象和元素引起用户的注意。以下介绍
  • 用ASP代码实现对access数据库的在线压缩处理,注意压缩前请备份数据库。我们知道每个一段时间压缩一下access数据库,可以减少数据库的
  • 我要说的内容都是非常基础的内容,高手就免看了,如果看了欢迎给点意见啊。新手或者对低层还不是很了解的人可以看看,帮助理解与记忆。XMLHttp
  • 在ASP中利用OWC(Office Web Components)控件可轻松实现各种图表功能,如饼图,簇状柱型图,折线图
  • 技巧之一:提高使用Request集合的效率 访问一个ASP集合来提取一个值是费时的、占用计算资源的过程。因为这个操作包含了一系列对相关集合的
  • [编者注:]提起数据库,第一个想到的公司,一般都会是Oracle(即甲骨文公司)。Oracle在数据库领域一直处于领先地位。Oracle关系
  • FLASH 全屏有二类四种:1、不用浏览器直接用FLASH播放器播放的类型:A、不显示FLASH播放器菜单栏的全屏(类似屏保效果),在第一帧
  • 一、“无”的哲学佛家讲究“因果报应”,有果必有应。此段看似与主题没有血缘关系,实际讲的是“因”。我个人比较喜欢老子的道家思想,并喜欢以其思想
手机版 网络编程 asp之家 www.aspxhome.com