双下划线查询、外键字段、各种查询
今日学习内容总结
双下划线查询#
参数介绍#
参数 | 意义 |
---|---|
__in | 是否在 |
__gt | 大于 |
__lt | 小于 |
__gte | 大于等于 |
__lte | 小于等于 |
__range | 在...之间,闭区间 |
__contains | 包含 |
__icontains | 包含(忽略大小写) |
__startswith | 以...开头 |
__endswith | 以...结尾 |
__year | 取出年份 |
__month | 取出月份 |
__day | 取出日期 |
__hour | 取出小时 |
__minute | 取出分钟 |
__second | 取出秒 |
__week_day | 一周的第几天 |
使用方法#
# 查询年龄大于20的用户
res = models.User.objects.filter(age__gt=20)
# 查询年龄小于20的用户
res = models.User.objects.filter(age__lt=20)
# 查询年龄大于等于20的用户
res = models.User.objects.filter(age__gte=20)
# 查询年龄小于等于20的用户
res = models.User.objects.filter(age__lte=20)
# 查询年龄是18,22,25的用户
res = models.User.objects.filter(age__in=[18,22,25])
# 查询年龄在18到26之间的用户
res = models.User.objects.filter(age__range=[18,26])
# 查询姓名中包含字母j的用户(区分大小写)
res = models.User.objects.filter(name__contains='j')
# 查询姓名中包含字母j的用户(忽略大小写)
res = models.User.objects.filter(name__icontains='j')
# 查询姓名中以字母j为开头的用户(区分大小写)
res = models.User.objects.filter(name__startswith='j')
# 查询姓名中以字母j为开头的用户(忽略大小写)
res = models.User.objects.filter(name__istartswith='j')
# 查询姓名中以字母j结尾的用户
res = models.User.objects.filter(name__endswith='j')
# 查询月份是5月的数据
res = models.User.objects.filter(op_time__month=5)
# 查询年份是22年的数据
res = models.User.objects.filter(op_time__year=2022)
外键字段的创建#
ForeignKey 一对多#
django orm外键字段针对一对多关系也是建在多的一方。
# 设置要关联的表,自动关联主键
to
# 自己设置要关联的表的字段
to_field\ti_fields
# 基于对象反向操作时,使用的字段名,用于代替原反向查询是的'表名小写_set',不建议使用
related_name
# 基于连表反向查询时使用的连接前缀,用于替换表名
related_query_name
# 当删除关联表中的数据时,当前表与其关联的行的行为
on_delete
# 是否在数据库中创建外键约束,默认为True。可以设置为False
db_constraint
on_delete参数值(1.x版本默认添加该参数, 2.x以后必须加上, 否则报错)。
# 例:on_delete=models.CASCADE
models.CASCADE
# 删除关联数据,与之关联也删除
models.DO_NOTHING
# 删除关联数据,什么都不做
models.PROTECT
# 删除关联数据,引发错误ProtectedError
models.SET_NULL
# 删除关联数据,与之关联的值设置为null(前提FK字段需要设置为可空)
models.SET_DEFAULT
# 删除关联数据,与之关联的值设置为默认值(前提FK字段需要设置默认值)
models.SET
# 删除关联数据
a. 与之关联的值设置为指定值,设置:models.SET(值)
b. 与之关联的值设置为可执行对象的返回值,设置:models.SET(可执行对象)
ManyToManyField 多对多#
django orm外键字段针对多对多关系 可以不用自己创建第三张表。
to
# 设置要关联的表
to_field
# 设置要关联的表的字段
related_query_name
# 反向查询操作时,使用的连接前缀,用于替换表名
symmetrical
# 仅用于多对多自关联时,指定内部是否创建反向操作的字段, 默认为True
through
# 手动创建第三张表,指定通过哪个表
through_fields
# 设置关联的字段
db_table
# 默认创建第三张表时,数据库中表的名称
OneToOneField 一对一#
django orm外键字段针对一对一关系 建在查询频率较高的表中
to
# 设置要关联的表
to_field
# 设置要关联的表的字段
on_delete
# 同ForeignKey字段
外键字段操作#
一对多、一对一外键字段操作
新增数据
models.Book.objects.create(title='聊斋志异', price=16987.22, publish_id=1) # 直接填写关联数据的主键值
publish_obj = models.Publish.objects.filter(pk=2).first()
models.Book.objects.create(title='资本论', price=56777.98, publish=publish_obj)
修改关系字段
models.Book.objects.filter(pk=1).update(publish_id=3)
publish_obj = models.Publish.objects.filter(pk=2).first()
models.Book.objects.filter(pk=1).update(publish=publish_obj)
多对多字段操作
1.第三张关系表创建数据
book_obj = models.Book.objects.filter(pk=1).first()
book_obj.authors.add()
括号内可以放主键值也可以放数据对象,并且都支持多个。
2.第三张关系表修改数据
book_obj.authors.set()
括号内必须是一个可迭代对象,元素同样支持主键值或者数据对象。
3.第三张关系表删除数据
book_obj.authors.remove()
括号内可以放主键值也可以放数据对象,并且都支持多个。
4.第三张关系表清空指定数据
book_obj.authors.clear()
括号内无需传值,直接清空当前表在第三张关系表中的绑定记录。
多表查询#
正向查询#
1. 正向查询按字段
2. 正向:外键字段在的一方查不在的一方
3. 如果返回结果多个还需要.all()
反向查询#
1. 反向查询按表名小写
2. 反向:外键字段不在的一方查在的一方
3. 如果返回结果多个还需要连接_set.all()
基于对象的跨表查询#
基于对象的跨表查询本质就是子查询即分步操作即可。
# 1.查询数据分析书籍对应的出版社
# 先获取书籍对象
book_obj = models.Book.objects.filter(title='数据分析').first()
# 再使用跨表查询
res = book_obj.publish
print(res)
# 2.查询python全栈开发对应的作者
# 先个获取书籍对象
book_obj = models.Book.objects.filter(title='python全栈').first()
# 再跨表
res = book_obj.authors.all() # 因为结果 为多个,如果不加all:app01.Author.None
print(res)
# 3.查询作者jason的详细信息
author_obj = models.Author.objects.filter(name='jason').first()
res = authors_obj.author_detail
print(res)
# 4.查询东方出版社出版的书籍
publish_obj = models.Publish.objects.filter(name='东方出版社').first()
res = publish_obj.book_set_all()
print(res)
# 5.查询jason编写的书籍
author_obj = models.Author.objects.filter(name='jason').first()
res = author_obj.book_set.all()
print(res)
# 6.查询电话是110的作者
author_detail_obj = models.AuthorDetail.objects.filter(phone=110).first()
res = author_detail_obj.author
print(res)
基于双下划线的跨表查询#
基于双下划线的跨表查询本质就是连表操作。
# 1.查询数据分析书籍对应的出版社名称以及出版地址
res = models.Book.objects.filter(title='数据分析').values('publish_name', 'publish_addr')
print(res)
# 2.查询python全栈开发对应的作者姓名和年龄
res = models.Book.objects.filter(title='python全栈开发').values('authors_name', 'authors_age')
print(res)
# 3. 查询作者jason的手机号和地址
res = models.Author.objects.filter(name='jason').values('author_detail_phone', 'author_datail_addr')
print(res)
# 4.查询东方出版社出版的书籍名称和价格
res = models.Publish.objects.filter(name='东方出版社').values('book_title', 'book_price')
print(res)
# 5.查询jason编写的书籍名称和日期
res = models.Author.objects.filter(name='jason').values('book_title', 'book_publish_time')
print(res)
# 6.查询电话是110的作者的姓名和年龄
res = models.AuthorDetail.objects.filter(phone=110).values('author_name', 'author_age')
双下线查询扩展#
基于双下划线的跨表查询的结果也可以是完整的数据对象。
手上有条件所在的表可以不被models点,直接点最终的目标数据对应的表。
# 1.查询数据分析书籍对应的出版社名称
res = models.Publish.objects.filter(book__title='数据分析').values('name')
print(res)
# 2.查询python全栈开发对应的作者姓名和年龄
res = models.Author.objects.filter(book_title='python全栈开发').values('name', 'age')
# 3.查询作者jason的手机号和地址
res = models.AuthorDetail.objects.filter(author_name='jason').values('phone', 'addr')
# 4.查询东方出版社出版的书籍名称和价格
res = models.Book.objects.filter(publish_name='东方出版社').values('title', 'price')
# 5.查询jason编写的书籍名称和日期
res = models.Book.objects.filter(author_name='jason').values('title', 'publish_time')
# 6.查询电话是110的作者的姓名和年龄
res = models.Author.objects.filter(author_detail_phone=110).values('name', 'age')
# 连续跨表操作
# 查询python全栈开发对应的作者的手机号
res = models.Book.objects.filter(title='python全栈开发').values('authors_author_detail_phone')
如何查看SQL语句#
1. 如果结果集对象是queryset 那么可以直接点query查看
2. 配置文件固定配置
适用面更广 只要执行了orm操作 都会打印内部SQL语句
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 25岁的心里话
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· 闲置电脑爆改个人服务器(超详细) #公网映射 #Vmware虚拟网络编辑器
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用