【Django学习】(六)ORM框架_关联模型_数据创建&查询&更新&删除&过滤

我们配置了ORM框架并初步创建了简单的模型类,接下来可以把之前的模型类进行优化

projects应用中的model.py,增加一些新的属性
 

class ProjectsModel(BaseModel):
    # 设置id为主键
    id = models.AutoField(primary_key=True, verbose_name="id主键", help_text="id主键")
    name=models.CharField(max_length=200,verbose_name="项目名",help_text="项目名")
    leader=models.CharField(max_length=20,verbose_name="负责人",help_text="负责人")
    tester=models.CharField(max_length=20,verbose_name="测试",help_text="测试")
    programmer=models.CharField(max_length=50,verbose_name="开发人员",help_text="开发人员")
    publish_app=models.CharField(max_length=100,verbose_name="发布应用",help_text="发布应用")
    desc=models.TextField(max_length=200,verbose_name="简要描述",help_text="简要描述",blank=True,null=True,default="")

    class Meta:
        db_table = 'tb_projects'
        verbose_name = '项目信息'
        verbose_name_plural = verbose_name

    def __str__(self):
        # a.必须返回一个字符串类型
        # b.在打印模型类对象时,会自动调用
        return self.name

再创建新应用interfaces,并且在全局配置表中进行注册

在models.py中定义类属性:

class InterfacesModel(BaseModel):
    # 在关系型数据库中,有哪些关联关系?
    # a.一对一
    # b.一(父表)对多(子表、从表)
    # c.多对多
    id = models.IntegerField(primary_key=True, verbose_name="id主键", help_text="id主键")
    name = models.CharField(max_length=200, verbose_name="接口名称", help_text="接口名称")
    tester = models.CharField(max_length=200, verbose_name="测试人员", help_text="测试人员")
    # a.可以使用ForeignKey来指定一对多的外键字段
    # b.需要在“多”的那一侧添加外键字段
    # c.第一个必传参数需要添加关联的父表,有两种添加方式:
    #   方式一,可以直接使用父表模型类
    # project = models.ForeignKey(ProjectsModel, on_delete=models.CASCADE)

    #   方式二,可以使用字符串(子应用名.父表模型类名)
    # d.第二个必传参数,需要on_delete指定删除父表记录时的子表该字段的处理方式
    #   CASCADE指定为当父表中某条记录删除之后,父表中这条记录所属的从表记录,会自动被删除
    #   SET_NULL指定为当父表中某条记录删除之后,父表中这条记录所属的从表记录,会自动设置为空,需同时设置null=True
    #   PROTECT指定为当父表中某条记录删除之后,会报错
    # e.数据表中,会创建名称为外键字段_id的字段名
    project = models.ForeignKey("projects.ProjectsModel", on_delete=models.CASCADE)

    # models.OneToOneField指定一对一的外键字段
    # models.ManyToManyField指定多对多的外键字段
    class Meta:
        db_table = "tb_interfaces"
        verbose_name = "接口表"
    def __str__(self):
        return self.name

先使用命令行造个数据(在pycharm中的Python Console控制台输入命令)
导入模型类

from projects.models import ProjectsModel

实例化模型类

res=ProjectsModel(name="111",leader="测试leader",tester="测试人",programmer="五星开发",publish_app="发布应用",desc="没有描述信息")

保存

res.save()

在视图函数里创建数据(create)

方法一:

 

 执行之后创建了数据

 说明:

  • 创建了模型类对象后,还没有执行sql语句
  • 必须要调用模型类对象.save()方法,才会执行sql语句并创建数据

方法二:

可以调用模型类.objects.create() 方法区创建模型类对象(一条记录)

data=ProjectsModel.objects.create(name="是个名字a a ",leader="测试leader",tester="测试人",programmer="五星开发",publish_app="发布应用",desc="没有描述信息")
  • 调用模型类.objects返回是的Manager对象 ,我们以后对数据库的操作,都可以在Manager基础上去操作
  • 然后调用Manger对象的create()方法,去创建模型类对象
  • 与方法一相比,无需再单独调用save()方法

数据的查询 (read)

方式一

查询某一条记录

  1. 如果查询条件是唯一键(比如主键id、unique=True的字段)
    1. 如果可以查到---->返回结果
    2. 如果查不到----->抛出异常
  2. 如果查询条件不是唯一键---->会抛出异常
  3. ORM中主键id字段,拥有一个pk别名

one_project = Projects.objects.get(pk=1)

 

使用id主键查询:

data=ProjectsModel.objects.get(id=1)

可以查询导数据:

如果使用非唯一键查询:就会抛出异常

查询多条记录

查询多条数据的时候我们可以调用all()方法,可以查询所有数据,返回的是一个查询集queryset

data_query=ProjectsModel.objects.all()

方式二

还可以使用filter过滤,返回的是一个查询集queryset

a.可以使用filter()方法,对数据库中的记录进行过滤(搜索)
b.会将满足条件的结果(模型类对象),添加到查询集中并返回
        id__gte=2 (id >= 2)
        id__in=[1, 2]
        one_qs = Projects.objects.filter(name__contains='2')
c.调用filter方法,可以使用各种过滤表达式参数
d.字段名__表达式可以对数据进行过滤(查询)
e.过滤表达式有很多种
        字段名__lt: <
        字段名__lte: <=
        字段名__gt: >
        字段名__gte: >=
        字段名__in: 包含某些值,使用序列类型(list、tuple)
        字段名__contain: 包含子字符串 字段名__icontain: 包含子字符串(忽略大小写)
        字段名__startswith: 包含以子字符串开头 字段名__istartswith: 包含以子字符串开头(忽略大小写)
        字段名__endswith: 包含以子字符串结尾 字段名__endswith: 包含以子字符串结尾(忽略大小写)

1、one_qs = Projects.objects.filter(id=2)
2、one_qs = Projects.objects.filter(id__exact=2)
3、one_qs = Projects.objects.filter(pk=2)
4、one_qs = Projects.objects.filter(id__in=[1, 2])
5、one_qs = Projects.objects.filter(name__startswith='x')
6、one_qs = Projects.objects.filter(name__contains='2')

其中1和2是等价的

one_qs = Projects.objects.filter(name__contains='2', desc__startswith='y')
one_qs = Projects.objects.filter(name__contains='2').filter(desc__startswith='y')
one_qs = Projects.objects.filter(name__contains='2').exclude(desc__startswith='x')
one_qs = Projects.objects.filter(Q(name__contains='3') | Q(desc__startswith='y'))

说明:

a.如果同一个filter方法中,添加多个过滤条件,那么每个条件之间为“与”的关系
b.查询集对象支持链式调用,可以在查询集对象上,多次调用filter
c.查询集链式调用,每个条件直接为“与”的关系

 下面使用Q查询中,多个Q对象之间如果使用“|”,每个条件之间为“或”关系 

one_qs = Projects.objects.filter(Q(name__contains='项目') | Q(leader='测试leader'))

 查询集queryset对象支持哪些操作呢??

查询集支持的操作:

  • 支持列表中的多数操作
    • len(qs) 获取查询集个数,推荐使用qs.count()方法
    • 切片 qs[a:b] 返回的依然为查询对象
    • qs[真整数索引],不支持负值索引
    • qs[0],推荐使用qs.first()方法
    • qs[qs.count() - 1],推荐使用qs.last()方法
    • qs.exist()方法,判断查询集是否为空,如果为空,返回False,否则返回True
  • list(qs),将查询集对象转化为列表
  • 查询集支持for操作,每次迭代返回模型类对象
  • 查询集为了增加性能,实现惰性查找的机制(只有真正需要数据的时候,才会执行sql语句)
  • 支持链式调用,可以多次调用filter或者exclude方法
  • 可以使用exclude将不满足条件的所有结果返回
    • one_qs = Projects.objects.exclude(id=1)

 数据的更新(update)

方式一
a.更新一条数据,可以先将数据查询出来,返回模型类对象
b.然后直接修改模型类对象的属性值
c.模型类对象调用save()方法,保持数据

pro = Projects.objects.get(pk=2)
pro.name = 'xxx金融类项目'
pro.save()
one_dict = {
    "id": pro.id,
    "name": pro.name
            }

方式二

可以使用filter方法().update(),批量修改多条数据

obj = Projects.objects.filter(Q(name__contains='2') | Q(name__contains='3')).update(leader='潇潇')

数据的删除(delete )

先将需要删除的模型类对象查询出来,然后调用delete()方法

one_obj = Projects.objects.get(id=2)
one_obj.delete()

 数据的排序操作

a.可以在查询集对象上调用.order_by()方法,可以对查询集中的模型类对象进行排序
b.order_by()方法,可以添加需要排序的字段名称,默认为升序(asc)
c.可以在字段名称前添加“-”,进行降序排列(desc)
e.如果有多个排序字段,可以给order_by()方法添加多个位置参数

f. 如果排序方法中存在多个相同字段的排序,则会以第二个字段的排序决定如何排序

 下面的排序意思是:查询出来的数据通过id降序,name升序展示出来

qs = Projects.objects.all().order_by('-id','name')

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

高老庄里的高小翠

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值