• Django:必会ORM查


    1.ORM常用字段

    • 在models.py,创建表中字段

    1.1AutoField

    • 自增的整形字段,必填参数primary_key=True,则成为数据库的主键。无该字段时,django自动创建。一个model不能有两个AutoField字段。

      from django.db import models
      class Person(models.Model):
      	pid = models.AutoField(primary_key=True)
      

    1.2 IntegerField

    • 一个整数类型。数值的范围是 -2147483648 ~ 2147483647。

       class Person(models.Model):
       	age = models.IntegerField()
      

    1.3 CharField

    • 字符类型,必须提供max_length参数。max_length表示字符的长度。

      class Person(models.Model):
      	name = models.CharField(max_length=32)
      

    1.4 DateField

    • 日期类型,日期格式为YYYY-MM-DD,相当于Python中的datetime.date的实例。

    • 参数:

      • auto_now:每次修改时修改为当前日期时间。
      • auto_now_add:新创建对象时自动添加当前日期时间。
      • 需要注意:default auto_now_add auto_now 之间是互斥的,只能填写一个
      class Person(models.Model):
      	birth = models.DateField(auto_now_add=True)
      

    1.5 DatetimeField

    • 日期时间字段,格式为YYYY-MM-DD HH:MM[:ss[.uuuuuu]][TZ],相当于Python中的datetime.datetime的实例。

      class Person(models.Model):
      	birth = models.DateTimeField(auto_now_add=True)
      

    1.6 BooleanField

    • 布尔值

      class Person(models.Model):
      	gender = models.BooleanField("性别",choices=((0,"男"),(1,"女")))
      

    1.7 DecimalField

    • 十进制小数

    • 参数:

      • max_digits 总长度
      • decimal_places 小数位数
      class Person(models.Model):
      	money = models.DecimalField(max_digits =5,decimal_places=3)
      

    1.8 TextField

    • 文本类型

    1.9 了解即可:

    1.BigAutoField
    	bigint自增列,必须填入参数 primary_key = True
    2。SmallIntegerField(IntegerField)
    	小整数 -32768 ~ 32767
    3.PositiveSmallIntegerField(PositiveIntegerRelDbTypeMixin, IntegerField)
    	正小整数 0 ~ 32767
    4.IntegerField(Field)
    	整数列(有符号的) -2147483648 ~ 2147483647
    5.PositiveIntegerField(PositiveIntegerRelDbTypeMixin, IntegerField)
    	正整数 0 ~ 2147483647
    6.BigIntegerField(IntegerField)
    	长整型(有符号的) -9223372036854775808 ~ 9223372036854775807
    7.NullBooleanField(Field)
    	可以为空的布尔值
    8.EmailField(CharField)
    	字符串类型,Django Admin以及ModelForm中提供验证机制
    9.IPAddressField(Field)
    	字符串类型,Django Admin以及ModelForm中提供验证 IPV4 机制
    10.GenericIPAddressField(Field)
    	字符串类型,Django Admin以及ModelForm中提供验证 Ipv4和Ipv6
    	参数:
    		 protocol,用于指定Ipv4或Ipv6, 'both',"ipv4","ipv6"
    		 unpack_ipv4, 如果指定为True,则输入::ffff:192.0.2.1时候,可解析为192.0.2.1,开启此功能,需要protocol="both"
    		 
    11.URLField(CharField)
    	字符串类型,Django Admin以及ModelForm中提供验证 URL
    12.SlugField(CharField)
    	字符串类型,Django Admin以及ModelForm中提供验证支持 字母、数字、下划线、连接符(减号)
    13.CommaSeparatedIntegerField(CharField)
    	
    14.UUIDField(Field)
         字符串类型,Django Admin以及ModelForm中提供对UUID格式的验证
    
    15.FilePathField(Field)
    	字符串,Django Admin以及ModelForm中提供读取文件夹下文件的功能
    	参数:
    		path,                      文件夹路径
    		match=None,                正则匹配
    		recursive=False,           递归下面的文件夹
    		allow_files=True,          允许文件
    		allow_folders=False,       允许文件夹
    
    16.FileField(Field)
         字符串,路径保存在数据库,文件上传到指定目录
         参数:
                upload_to = ""      上传文件的保存路径
                storage = None      存储组件,默认django.core.files.storage.FileSystemStorage
    
    17.ImageField(FileField)
          字符串,路径保存在数据库,文件上传到指定目录
          参数:
                upload_to = ""      上传文件的保存路径
                storage = None      存储组件,默认django.core.files.storage.FileSystemStorage
                width_field=None,   上传图片的高度保存的数据库字段名(字符串)
                height_field=None   上传图片的宽度保存的数据库字段名(字符串)
    
    
    18.TimeField(DateTimeCheckMixin, Field)
         时间格式      HH:MM[:ss[.uuuuuu]]
    
    19.DurationField(Field)
         长整数,时间间隔,数据库中按照bigint存储,ORM中获取的值为datetime.timedelta类型
    
    20.FloatField(Field)
         浮点型
    
    21.DecimalField(Field)
         10进制小数
         参数:
            max_digits,小数总长度
            decimal_places,小数位长度
    
    22.BinaryField(Field)
          二进制类型
    

    注意:当model中如果没有自增列,则自动回创建一个列名为id的列

    2.自定义字段

    • 在models.py自定义一个char字段类型
    class MyCharField(models.Field):
        def __init__(self,max_length,*args,**kwargs):
            self.max_length = max_length
            super(MyCharField,self).__init__(max_length=max_length,*args,**kwargs)
        def db_type(self,connection):
            return "char(%s)"%(self.max_length)
    
    • 使用自定义字段:
    class Person(models.Model):
    	iphone = MyCharField(max_length=11)
    

    3.Django 中超级用户的激活和表的注册

    • 在Terminal 输入命令 python3 manage.py createsuperuser

    • 表的注册:在admin.py文件输入

      from django.contrib import admin
      from app01 import models
      
      admin.site.register(models.Person)
      

    4.字段参数的设置

    • 常用字段参数设置
    null			数据库中字段是否可以为空
    db_column		 数据库中字段的列名
    default			 数据库中字段的默认值
    primary_key       数据库中字段是否为主键
    db_index          数据库中字段是否可以建立索引
    unique            数据库中字段是否可以建立唯一索引
    verbose_name        Admin中显示的字段名称
    blank               Admin中是否允许用户输入为空
    editable            Admin中是否可以编辑
    help_text           Admin中该字段的提示信息
    choices             Admin中显示选择框的内容,用不变动的数据放在内存中从而避免跨表操作
    index_together     联合索引
    unique_together    联合唯一索引
    
    • null与blank

      class Person(models.Model):
      	iphone = MyCharField(max_length=11,null=True)  #表示数据库可以为null,默认null为False
      #设置改变数据库属性必须执行数据库迁移命令如null,改变Django内form表单可以不用执行数据库命令,如blank
      # 一般blank和null同时出现。blank=True  from表单填写时为可以为空
      
    • db_column

      class Person(models.Model):
      	name = models.CharField(max_length=32,db_column="username")
      #django字段显示name,在数据库中显示为username
      
    • default

      class Person(models.Model):
      	age = models.IntegerField(default=18)
      #需要注意:default auto_now_add auto_now 之间是互斥的,只能填写一个
      
    • verbose_name/db_table/verbose_name_plural

      class Meta:
          db_table = "个人管理"
          verbose_name = "个人信息表"
          verbose_name_plural = "哈哈"
      #verbose_name也可以给字段设置admin显示的内容
      age = models.IntegerField(default=18, verbose_name='年纪', editable=True)
      

      verbose_name_plural:

      verbose_name:

    ​ db_table:

    • editable

      #当给age设置editable为Fasle,则admin页面将不会显示age
      class Person(models.Model):
      	age = models.IntegerField(default=18, verbose_name='年纪', editable=False)
      
    • help_text帮助提示信息

      class Person(models.Model):
      	age = models.IntegerField(default=18, verbose_name='年纪',help_text="不是农历岁数")
      
      

      显示在admin:

    • choices

      class Person(models.Model):
      	gender = models.BooleanField("性别",choices=((0,"男"),(1,"女")))
      

      显示效果:

    • class Meta常用参数

      model = models.Student   #对应的Model中的类
      fields = "__all__" #字段,如果是__all__,就是表示列出所有的字段
      exclude = None #排除的字段
      labels = None #提示信息
      help_texts = None #帮助提示信息
      widgets = None  #自定义插件
      error_message = None #自定义错误信息
      

    5.Model Meta 参数设置

    • 不经常用,如果有特殊需要可以使用
    class Person(models.Model):
    	......
    	class Meta:
            db_table = "个人管理"
            verbose_name = "个人信息表"
            verbose_name_plural = "哈哈"
            #联合索引
            index_together=[
                ("name","age"),
            ]
            #联合唯一索引
            unique_together = (("iphone","birth"),)
            
    

    6.在交互模式下创建数据

    • pycharm内置交互模式启动Django,可以执行代码。
    增:
    obj = models.Person.objects.create(name="xjk",iphone="13589306703",gender=0)
    删:
    obj.delete()
    改:
    obj.update(name="xujunkai")
    查:
    obj = models.Person.objects.filter(pk=5)
    

    7.ORM查询必知(13条)

    • 在项目目录下创建文件夹
    • 再在文件夹下创建py文件
    • 导入模块(先配置环境再django.setup())

    #必须按照这个顺序,否则报错
    import os
    import django
    os.environ.setdefault("DJANGO_SETTINGS_MODULE","mro_lianxi.settings")#mro_lianxi为项目名称
    django.setup()
    from app01 import models
    
    django.core.exceptions.ImproperlyConfigured: Requested setting DEFAULT_INDEX_TABLESPACE, but settings are not configured
    
    django.core.exceptions.AppRegistryNotReady: Apps aren't loaded yet.
    
    • 查询
    #all()   获取所有的数据    --->QuerySet 对象列表
    ret = models.Person.objects.all()
    print(ret)
    
    #get()  获取满足条件的一个数据 ---->对象(获取不到或者多个报错)
    ret = models.Person.objects.get(pk=1)
    print(ret)
    
    #filter()  获取满足条件所有数据 ---> QuerySet 对象列表
    ret = models.Person.objects.filter(pk=1)
    print(ret)
    
    #exclude()  获取不满足条件的所有数据 ---> QuerySet  对象列表
    ret = models.Person.objects.exclude(pk=1)
    print(ret)
    
    #values()    获取对象所有的字段和字段的值     QuerySet[{},{}]
    #values(字段)    获取对象指定的字段和字段值    QuerySet[{},{}]
    ret = models.Person.objects.values()
    print(ret)
    ret = models.Person.objects.values("pid","name")
    print(ret)
    
    # values_list()  拿到对象所有的字段值  QuerySet[(),()]
    ret = models.Person.objects.values()
    print(ret)
    
    # order_by 排序  '-'号代表降序  ----> QuerySet[(),()]
    ret = models.Person.objects.order_by("age","-pid")#按照age升序,pid降序
    print(ret)
    
    #reverse 反向排序  只对已经排序的QuerySet进行反转
    ret = models.Person.objects.all().order_by("pk").reverse()
    print(ret)
    
    #distinct 去重    完全相同才能去重... 拿到values 是一个QuerySet对象,里面装字典键age, 给age相同去重
    ret = models.Person.objects.values("age").distinct()
    print(ret)
    
    #count 计数
    ret = models.Person.objects.all().count()
    print(ret)
    
    #first 取第一个元素  没有元素 None
    ret = models.Person.objects.all().values().first()
    print(ret)
    
    #last 取最后一个元素  没有元素None
    ret = models.Person.objects.all().values().last()
    print(ret)
    
    # exists 查询数据是否存在
    ret = models.Person.objects.filter(pk=10000).exists()
    print(ret)
    

    注意

    class Meta:
         ordering = ("pk") #默认排序 此处有坑
    #不要再Meta设置排序,这样会导致后面使用其他方法查表,查询无效
    #如:
    	distinct  去重   失效
    
    • 小结:
    1.返回QuerySet
        all()    
        filter()
        exclude()
        values()  
        values_list() 
        order_by() 
        reverse() 
        distinct()
    2.返回一个对象
    	get() 
    	first()
    	last()
    3.返回数字
    	count()
    4.返回布尔值
    	exists()
    

    8.单表查询之神奇的双下划线

    #gt
    # 大于(greater than)
    #获取pk大于1。
    ret = models.Person.objects.filter(pk__gt=1)
    print(ret)
    
    #lt
    #小于(less than)
    #获取pk小于3
    ret = models.Person.objects.filter(pk__lt=3)
    print(ret)
    
    #gte
    #大于等于(greater than  equal)
    #获取pk大于等于2
    ret = models.Person.objects.filter(pk__gte=2)
    print(ret)
    
    #lte
    #小于等于(less than  equal)
    #获取pk 小于等于3
    ret = models.Person.objects.filter(pk__lte=3)
    print(ret)
    
    #range
    #范围
    #获取pk 在2~4之间的对象
    ret = models.Person.objects.filter(pk__range=[2,4])
    print(ret)
    
    #in
    #成员判断
    #获取pk 在[1,2,5,10]里的
    ret = models.Person.objects.filter(pk__in=[1,2,5,10])
    print(ret)
    
    #contains
    #获取name有a的对象
    ret = models.Person.objects.filter(name__contains="a")
    print(ret)
    
    #icontains
    #获取name有a的,不区分大小写
    ret = models.Person.objects.filter(name__icontains="a")
    print(ret)
    
    #startswith
    #获取name以a开头的
    ret = models.Person.objects.filter(name__startswith='a')  # 以什么开头
    print(ret)
    
    #istartswith
    #获取name以a开头的,不区分大小写
    ret = models.Person.objects.filter(name__istartswith='a')
    print(ret)
    
    #endswith
    #获取name以a结尾的对象
    ret = models.Person.objects.filter(name__endswith='a')  # 以什么结尾
    print(ret)
    
    #iendswith
    #获取name 以a结尾的对象,不区分大小写
    ret = models.Person.objects.filter(name__iendswith='a')
    print(ret)
    
    #year
    #获取birth里的year 为2019的对象
    ret  = models.Person.objects.filter(birth__year='2019')
    print(ret)
    
    #contains
    #获取birth年月日为2017-06-24的对象
    #会有warning警告
    ret  = models.Person.objects.filter(birth__contains='2017-06-24')
    print(ret)
    
    #isnull
    #获取iphone 为是null的对象
    ret  = models.Person.objects.filter(iphone__isnull=True)
    print(ret)
    

    9.外键的操作

    • 首先创建2张外键关联表
    • 代码:
    #models.py
    class Publisher(models.Model):
        name = models.CharField(max_length=32)
        def __str__(self):
            return self.name
    class Book(models.Model):
        title = models.CharField(max_length=32)
        pub = models.ForeignKey(Publisher,on_delete=models.CASCADE)
        def __str__(self):
            return self.title
    
    

    • 在orm_test下创建py文件,并导入模块

      import os
      import django
      
      os.environ.setdefault("DJANGO_SETTINGS_MODULE","mro_lianxi.settings")
      django.setup()
      
      from app01 import models
      
    • 基于对象的查询

      #正向查找(Book有关联的外键,先查询有外键关联的)
      #通过查书的名字,从而查到出版社
      book_obj = models.Book.objects.get(title="Go基础")
      print(book_obj.pub)
      #图灵出版社
      
      #反向查询 (类名小写_set)
      #通过查询出版社--->来查询到出版的书
      pub_obj = models.Publisher.objects.get(pk=2)
      print(pub_obj.book_set.all())
      
      
      
      
    • related_name使用

      #models.py
      class Publisher(models.Model):
          name = models.CharField(max_length=32)
          def __str__(self):
              return self.name
      class Book(models.Model):
          title = models.CharField(max_length=32)
          pub = models.ForeignKey(Publisher,related_name='books',on_delete=models.CASCADE)
          def __str__(self):
              return self.title
      #当把Book的pub字段设置related_name='books',则反向查找方式更改为
      pub_obj = models.Publisher.objects.get(pk=2)
      print(pub_obj.books.all())
      
    • 基于字段的查询

      #查询title为Go基础的对象
      ret = models.Book.objects.filter(title="Go基础")
      print(ret)
      #查询图灵出版社出版的书
      ret = models.Book.objects.filter(pub__name="图灵出版社")
      print(ret)
      
      #当related_name = "books"
      #反向查找:
      ret= models.Publisher.objects.filter(books__title='Go基础')
      print(ret)
      
      
      #当设置related_query_name="mybook" 和related_name = "books"
      
      ret= models.Publisher.objects.filter(mybook__title='Go基础')
      print(ret)
      

    练习题:https://www.cnblogs.com/maple-shaw/articles/9414626.html

  • 相关阅读:
    1015词法分析
    0909作业
    华为云专家来公司
    SVN与Git的优点差异比较
    eclipse快捷键大全
    Servlet,HttpServletRequest 和 HttpServletResponse
    XML
    JDBC
    XMIND快捷键
    java数据
  • 原文地址:https://www.cnblogs.com/xujunkai/p/11847447.html
Copyright © 2020-2023  润新知