第58天:django学习(七)

orm增删改查

        在model.py中建表,然后迁移数据库

from django.db import models
​
# Create your models here.
​
class Book(models.Model):
    title = models.CharField(max_length=32)
    price = models.DecimalField(max_digits=8, decimal_places=2)
    publish_date = models.DateField(auto_now_add=True)
​
    # 一对多
    publish = models.ForeignKey(to='Publish', on_delete=models.DO_NOTHING)
    # 多对多
    authors = models.ManyToManyField(to='Author')
​
class Publish(models.Model):
    name = models.CharField(max_length=32)
    addr = models.CharField(max_length=64)
​
​
    def __str__(self):
        return self.name
​
​
class Author(models.Model):
    name = models.CharField(max_length=32)
    age = models.IntegerField()
    # 一对一
    author_detail = models.OneToOneField(to='AuthorDetail',on_delete=models.DO_NOTHING)
​
​
class AuthorDetail(models.Model):
    phone = models.BigIntegerField()
    addr = models.CharField(max_length=64)

        在测试文件test.py中启动django和导入应用下的model.py

import os
​
# Create your tests here.
​
if __name__ == '__main__':
    os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'day58_dj.settings')
    import django
    django.setup()
    from app01 import models

一对多外键的增删改查

        增加数据

models.Book.objects.create(title='论语', price=45, publish_id=1)

        删除数据

models.Book.objects.filter(pk=1).delete()

        修改数据

models.Book.objects.filter(pk=1).update(price=35)

        查询数据

res = models.Book.objects.all()
print(res)

多对多外键的增删改查

        增加数据

book_obj = models.Book.objects.filter(pk=1).first()
book_obj.authors.add(1)

        同时也支持对象的添加方式

author_obj1 = models. Author. objects. filter(pk=1). first() 
author_obj2 = models. Author. objects. filter(pk=2). first() 
author_obj3 = models. Author. objects. filter(pk=3). first()
book_obj.authors.add(author_obj1, author_obj2, author_obj3)

        删除数据

book_obj.authors.remove([2, 3])

        同时也支持对象的删除方式

book_obj.authors.remove([author_obj1, author_obj2, author_obj3])

        修改数据

book_obj.authors.set([2, 3])

        同时也支持对象的修改方式

book_obj.authors.set([author_obj1, author_obj2, author_obj3])

        清空数据

book_obj.authors.clear()

多表查询

子查询(基于对象的跨表查询)

正反向的概念

        正向查询

        带有外键字段的表去查不带外键字段的表,通过外键字段查询

        反向查询

        不带有外键字段的表去查带外键字段的表,通过表名小写或表名小写_set查询

        查询书籍主键为1的出版社

        这是正向查询,按外键字段查询

res=models.Book.objects.filter(pk=1).first()
print(res.publish)
  • 输出结果就是出版社对象

        查询书籍主键为2的作者

        这是正向查询,按外键字段查询

res=models.Book.objects.filter(pk=2).first()
print(res.authors.all())

        查出来的是结果要用for循环进行打印

for i in res.authors.all():
    print(i.name)
        查询作者kevin的电话号码

        这是正向查询,按外键字段查询

res=models.Author.objects.filter(name='kevin').first()
print(res.author_detail.phone)
        查询出版社是北京出版社出版的书

        这是反向查询,按表名小写查询

res=models.Publish.objects.filter(name='北京出版社').first()
print(res.book_set.all())
        查询作者是kevin的书

        这是反向查询,按表名小写查询

res=models.Author.objects.filter(name='kevin').first()
print(res.book_set.all())
        查询手机号是110的作者姓名

        这是反向查询,按表名小写查询

res=models.AuthorDetail.objects.filter(phone=110).first()
print (res.author.name)
  • 当查询结果可以有多个的时候,就必须加set.all()

  • 当你的结果只有一个的时候,不需要加set.all()

联表查询(基于双下划线的跨表查询)

        查询jason的手机号和作者姓名

        正向查询,按外键字段查询

res = models.Author.objects.filter(name='jason').values('author_detail__phone','name')
print(res)

        反向查询,按表名小写查询

res=models.AuthorDetail.objects.filter(
    author__name='jason'
).values('phone','author__name')
print(res)
        查询书籍主键为1的出版社名称和书的名称

        正向查询,按外键字段查询

res = models.Book.objects.filter(pk=1).values('title','publish__name')
print(res)

        反向查询,按表名小写查询

res = models.Publish.objects.filter(book__id=1).values('name','book__title')
print(res)
        查询书籍主键为1的作者姓名

        正向查询,按外键字段查询

res = models.Book.objects.filter(pk=1).values('authors__name')
print(res)

        反向查询,按表名小写查询

res = models.Author.objects.filter(book__id=1).values('name')
print(res)
        查询书籍主键是1的作者的手机号

        这是正向查询,按外键字段查询,且跨了多张表进行查询,总共使用了三种表

res = models.Book.objects.filter(pk=1).values('authors__author_detail__phone')
print(res)

分组

聚合查询

        作用

        聚合查询通常情况下都是配合分组一起使用的

        导入

from app01 import models
from django.db.models import Max,Min,Sum,Count,Avg
        所有书的平均价格
res = models.Book.objects.aggregate(Avg('price'))
print(res)
        导入的方法一次性使用
res=models.Book.objects.aggregate(
    Max('price'),Min('price'),Sum('price'),Count('pk'),Avg('price')
)
print(res)

分组查询

        统计每一本书的作者个数
res=models.Book.objects.annotate(
    author_num=Count('authors')
).values('title','author_num')
print(res)
        统计每个出版社卖的最便宜的书的价格
res=models.Publish.objects.annotate(
    min_price=Min('book__price')
).values('name','min_price')
print(res)
        统计不止一个作者的图书
  • 先按照图书分组 求每一本书对应的作者个数

  • 过滤出不止一个作者的图书

res=models.Book.objects.annotate(
    author_num=Count('authors')
).filter(author_num__gt=1).values('title','author_num')
print(res)
        查询每个作者出的书的总价格
res=models.Author.objects.annotate(
    sum_price=Sum('book__price')
).values('name','sum_price')
print(res)

F与Q查询

前期准备

        在model.py中Book表中添加字段,再次迁移数据库

maichu=models.IntegerField(default=1000)
kucun=models.IntegerField(default=2000) 

F查询

        作用

        能够直接获取到表中某个字段对应的数据

        导入

from django.db.models import F
from django.db.models.functions import Concat
from django.db.models import Value
        查询卖出数大于库存数的书籍
res = models.Book.objects.filter(maichu__gt=F('kucun'))
print(res)
        将所有书籍的价格提升500块
models.Book.objects.update(price=F('price') + 500)
        将所有书的名称后面加上爆款两个字
models.Book.objects.update(title=Concat(F('title'), Value('爆款')))
  • 在操作字符类型的数据的时候 F不能够直接做到字符串的拼接

Q查询

        导入

from django.db.models import Q
        例:查询卖出数大于100或者价格小于600的书籍
res = models.Book.objects.filter(maichu__gt=100,price__lt=600)
  • 之前的查询方法,filter括号内多个参数是and关系

res = models.Book.objects.filter(Q(maichu__gt=100),Q(price__lt=600))
  • Q包裹逗号分割 还是and关系

res = models.Book.objects.filter(Q(maichu__gt=100)|Q(price__lt=600))
  • 这是or关系

res = models.Book.objects.filter(~Q(maichu__gt=100)|Q(price__lt=600))
  • 这是not关系

Q的高阶用法

        能够将查询条件的左边也变成字符串的形式

q = Q()
q.connector = 'or'
q.children.append(('maichu__gt',100))
q.children.append(('price__lt',600))
res = models.Book.objects.filter(q) 
print(res)

相关推荐

  1. 58django学习

    2023-12-08 05:58:04       34 阅读
  2. 57django学习(六)

    2023-12-08 05:58:04       31 阅读
  3. 59django学习(八)

    2023-12-08 05:58:04       32 阅读
  4. 56django学习(五)

    2023-12-08 05:58:04       34 阅读
  5. 55django学习(四)

    2023-12-08 05:58:04       37 阅读
  6. 63-django学习(十二)

    2023-12-08 05:58:04       36 阅读
  7. 62django学习(十一)

    2023-12-08 05:58:04       34 阅读

最近更新

  1. TCP协议是安全的吗?

    2023-12-08 05:58:04       18 阅读
  2. 阿里云服务器执行yum,一直下载docker-ce-stable失败

    2023-12-08 05:58:04       19 阅读
  3. 【Python教程】压缩PDF文件大小

    2023-12-08 05:58:04       19 阅读
  4. 通过文章id递归查询所有评论(xml)

    2023-12-08 05:58:04       20 阅读

热门阅读

  1. vue+django 开发环境跨域前后端联调配置

    2023-12-08 05:58:04       42 阅读
  2. RabbitMQ

    RabbitMQ

    2023-12-08 05:58:04      42 阅读
  3. block-recurrent-transformer-pytorch 学习笔记

    2023-12-08 05:58:04       37 阅读
  4. js事件流模型

    2023-12-08 05:58:04       45 阅读
  5. MySql常用面试题

    2023-12-08 05:58:04       32 阅读
  6. 剑指 Offer(第2版)面试题 27:二叉树的镜像

    2023-12-08 05:58:04       42 阅读
  7. 如何进行多ip服务器租用?

    2023-12-08 05:58:04       37 阅读
  8. linux-tar命令、解压、压缩

    2023-12-08 05:58:04       38 阅读
  9. Linux硬链接和软连接是什么?

    2023-12-08 05:58:04       41 阅读
  10. Python 中 Thread 线程的用法

    2023-12-08 05:58:04       37 阅读
  11. [linux] 解压缩xz

    2023-12-08 05:58:04       39 阅读
  12. 中国证券交易所有哪些

    2023-12-08 05:58:04       27 阅读
  13. 贝蒂的捣蛋小游戏~(C语言)

    2023-12-08 05:58:04       35 阅读