django 3.2.13
一、数据库初始化
1.配置
目录:项目目录/setting.py
写入配置:
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.postgresql',
'NAME': 'postgres', # 数据库名称
'USER': 'postgres', # 登录数据库的用户名
'PASSWORD': ' ',# 登录数据库的密码
'HOST': '127.0.0.1', # 数据库服务器的主机地址(默认本机为127.0.0.1)
'PORT': '5432', # 数据库服务的端口号(默认为5432)
}
}
2.创建模型
目录:项目目录/app目录/models.py
class Question(models.Model):
question_text = models.CharField(max_length=200)
pub_date = models.DateTimeField('date published')
def __str__(self):
return self.question_text
class Choice(models.Model):
question = models.ForeignKey(Question, on_delete=models.CASCADE)
choice_text = models.CharField(max_length=200)
votes = models.IntegerField(default=0)
数据类型图:
数据类型参数:
注意:__str__方法用于返回对象的描述信息,如果不使用__str__方法,直接print,或者return,返回的是对象的内存地址
zhangsan = Student("张", 2200)
print(zhangsan) # 如果Student这个class类,没有写__str__方法,输出的是内存地址,但是加上__str__就是值
3.数据库内容创建(迁移)
前要:第一次迁移前看一下user表结构更改
- 生成脚本文件:
python3 manage.py makemigrations
- 执行脚本文件(操作数据库):
python3 manage.py migrate
注意:Ⅰ.比如数据库表单已经生成,需要删除一个字段可以直接再次执行上诉命令;Ⅱ.添加字段必须要为其设置默认值,否则django会进行询问(可写入默认值,可退出该操作)
二、自定义脚本
首先:pip install django-extensions
其次:写入setting.py 文件中的INSTALLED_APPS中添加django_extensions
。
创建:文件add.py
编辑自定义脚本如下:
import random
import string
from Main.models import Like
def generate_random_codes():
for obj in Like.objects.filter(code=None):
obj.code = code
obj.save()
generate_random_codes()
执行:python manage.py runscript add.py
三、增删改查
具体:书Django Web应用开发实战p161开始
1.增
from .models import Article
Article.objects.create(title="My first article", body="My first article body")
2.删
2.1 删一条
from .models import Article
Article.objects.get(title="java").delete()
2.2 删多条(条件满足的)
from .models import Article
Article.objects.filter(title="java").delete()
2.3 on_delete删除模式
写法:on_delete=models.CASCADE
参数:
- PROTECT:如果删除的数据设有外键且关联其它数据表,就提示删除错误,其实在外键上就是不许删除
- CASCADE:级联删除,删除与主键关联表的数据,主键所在表的内容也会被删除,反之则不会
- SET_NULL:置空模式,删除的时候,外键字段被设置为空,前提就是null=True
- SET_DEFAULT:置默认值,删除的时候,外键字段设置为默认值,前提就是default=‘默认值’(此时不能出现null=True,一对一特殊关系慎用)
3.改
3.1 改一条
# get方式不能用update
from .models import Article
a = Article.objects.get(id=1)
a.foreign_id=3
a.save()
3.2 改多条(条件满足的)
from .models import Article
Article.objects.filter(title='java').update(title='django')
4.查
4.1 查方法
4.1.1 查全部
from .models import Article
Article.objects.all()
4.1.2 查单个
from .models import Article
article = Article.objects.get(id=1)
article = Article.objects.filter(id=1).first() # 没有返回None
4.1.3 查多个
from .models import Article
article = Article.objects.filter(name='jack')
4.1.4 数量查询
from .models import Article
article = Article.objects.filter(name='jack').count()
4.1.5 多个条件
4.1.5.1 and
from .models import Article
article = Article.objects.filter(name='jack',id=5)
4.1.5.2 or
from .models import Article
from django.db.models import Q
article = Article.objects.filter(Q(name='jack')|Q(passwd='5963'))
4.1.5.3 不等于查询
from .models import Article
article = Article.objects.filter(~Q(name='jack'))
4.2 谓语查询[模糊查询、大小、范围]
4.2.1 模糊查询
# 关键__contains表示模糊查询
Teacher.objects.filter(name__contains='8')
4.2.2 指定开头结尾
# 表示以9开头
a = Teacher.objects.filter(name__startswith='9')
# 表示以9结尾
a = Teacher.objects.filter(name__endswith='9')
4.2.3 大小比较
# 大于8
a = Teacher.objects.filter(id__gt=8)
# 大于等于8
a = Teacher.objects.filter(id__gte=8)
# 小于8
a = Teacher.objects.filter(id__lt=8)
# 小于等于8
a = Teacher.objects.filter(id__lte=8)
4.2.4 字段在某列表
# 字段在某个列表中 __in=[8,9,10],下面表示,id号在[8,9,10]列表里面,通俗讲此处就是id=8,id=9,id=10的情况
a = Teacher.objects.filter(id__in=[8,9,10])
4.2.5 数字字段在某个范围内
# id在8-15之间的都取出
a = Teacher.objects.filter(id__range=(8,15))
4.3 F对象
4.3.1 字段自增
解释:普通的自增什么的都需要先提取出来再增加,明显浪费资源,使用此方法,数据库直接会操作
# 让id=8这个数据里面的time字段增加100
from django.db.models import F
Student.objects.filter(id=8).update(time=F('time')+100)
4.3.2 两个数据比较
# 对比所有信息,取出其中id号小于time对应内容的数据
from django.db.models import F
Student.objects.filter(id__lt=F('time'))
4.4 聚合查询
4.4.1 聚合不分组
解释:也就是全部都在一起来算,返回的数据为字典,无需序列化
from django.db.models import Avg,Max,Min,Count,Sum # 统计平均值,最大值,最小值,数量,和
Student.objects.aggregate(sum=Count('time')) # {'sum': 345354345}
Student.objects.aggregate(sum=Max('time')) # {'sum': 3}
4.4.2 聚合分组
解释:某些数据来进行运算,返回的数据为字典,无需序列化
from django.db.models import Avg,Max,Min,Count,Sum
# 格式:某个组.aggregate(sum=Count('time'))
Student.objects.filter(id__lt=F('time')).aggregate(sum=Count('time')) # {'sum': 3}
四、一对一、一对多、多对多
知识点:
- 正向查询:
Info.objects.all()[0].foreign #info是有外键的表,foreign是定义的外键参数名
- 反向查询:
# 一对一
>>> a = User.objects.all()[0] # User是外键关联表
>>> a.back #back是设置的外键属性related_name
<InfoTwo: 1>
# 一对多
>>> a = Father.objects.all()[0]# Teacher是外键关联表
>>> a.back.all() #back是设置的外键属性related_name
<QuerySet [<Student: 563>, <Student: 563>]>
1.一对一
关系:人的身份证与人的关系,一一对应不可重复
关键概念:
- 外键:其也属于一个键值,是真实在表格里面存在的,外键对应的内容是另一个表的主键
- 正向查询:在外键所在表查询到,与外键关联的表内容
- 反向查询:在与外键关联的表,查询到外键所在表内容
知识点:
- OneToOneField:
Info= models.OneToOneField(User, on_delete=models.CASCADE,related_name=‘back’) # 用于一对一查询
设置外键:
-
Info.objects.create(id=100,passwd='00',time=12,foreign_id=4) #确保关联表已经有数据
关键是注意这个名字,与models.py里面定义的不一样
from django.db import models
# Create your models here.
class User(models.Model):
id = models.AutoField(primary_key=True)
name = models.CharField(max_length=20)
def __str__(self):
return self.name # 必须是字符串
class Info(models.Model):
id = models.AutoField(primary_key=True)
passwd = models.CharField(max_length=30)
time = models.IntegerField()
foreign = models.OneToOneField(User, on_delete=models.CASCADE,related_name=‘back’) # on_delete解释看二、增删改查 2.删
def __str__(self):
return self.passwd # 必须是字符串
2.一对多
关系:父亲与孩子的关系,一个父亲有多个孩子,一个孩子只有一个父亲
知识点:
- ForeignKey:
foreign = models.ForeignKey(Teacher, on_delete=models.CASCADE,related_name=‘back’)
设置外键:
-
Son.objects.create(id=100,passwd='00',time=12,foreign_id=4) #确保关联表已经有数据
关键是注意这个名字,与models.py里面定义的不一样
class Father(models.Model):
id = models.AutoField(primary_key=True)
name = models.CharField(max_length=20)
def __str__(self):
return self.name
class Son(models.Model):
id = models.AutoField(primary_key=True)
passwd = models.CharField(max_length=30)
time = models.IntegerField()
foreign = models.ForeignKey(Teacher, on_delete=models.CASCADE,related_name=‘back’)# on_delete解释看二、增删改查 2.删
def __str__(self):
return self.passwd
3.多对多
关系:老师和学生的关系,一个老师有多个学生,一个学生有多个老师
原理:多对多通过创建中间表格确定对应关系
设置外键:
- 初始化:
Student.objects.get(id=1).foreign.set([1,2,3])# 1,2,3默认都是与Student关联表的主键(set的特点:此例设置的Teacher的id的1,2,3关联到Student的id=1上面。如果原关系为1,2会直接改为1,2,3;如果原关系为1,2,3,4,5也会直接改为1,2,3) 总结:既能增加又能删除
- 增加:
Student.objects.get(id=1).foreign.add(1,2)# 1,2默认都是与Student关联表的主键
- 删除:
Student.objects.get(id=1).foreign.remove(1)# 1默认都是与Student关联表的主键
- 清空关系:
Student.objects.get(id=1).foreign.clear()
class Teacher(models.Model):
id = models.AutoField()
name = models.CharField(max_length=20, primary_key=True)
def __str__(self):
return self.name
class Student(models.Model):
id = models.AutoField(primary_key=True)
passwd = models.CharField(max_length=30)
time = models.IntegerField()
foreign = models.ManyToManyField(Father, on_delete=models.CASCADE, related_name='back')
def __str__(self):
return self.passwd