响应式的网站做优化好吗,云存储wordpress,辽宁建设工程信息网新域名,梧州门户网站模型基础#xff1a;
字段类型#xff1a;
django根据属性的类型确定以下信息
当前选择的数据库⽀持字段的类型渲染管理表单时使⽤的默认html控件在管理站点最低限度的验证django会为表增加⾃动增⻓的主键列#xff0c;每个模型只能有⼀个主键列#xff0c;如果使⽤选项…模型基础
字段类型
django根据属性的类型确定以下信息
当前选择的数据库⽀持字段的类型渲染管理表单时使⽤的默认html控件在管理站点最低限度的验证django会为表增加⾃动增⻓的主键列每个模型只能有⼀个主键列如果使⽤选项设置某属性为主键列后则django不会再⽣成默认的主键列。
属性命名限制
·遵循标识符规则 ·由于django的查询⽅式不允许使⽤连续的下划线 定义属性时需要字段类型字段类型被定义在django.db.models.fields⽬录下为了⽅便使⽤被导⼊到django.db.models中
使⽤⽅式
导⼊from django.db import models通过models.Field创建字段类型的对象赋值给属性
逻辑删除和物理删除
对于重要数据都做逻辑删除不做物理删除实现⽅法是定义is_delete属性类型为BooleanField默认值为False。(物理删除就是真正对数据库进行操作逻辑删除就是打标记筛选一下就可以)。
is_delete models.BooleanField(defaultFalse)常⽤字段类型 AutoField ·⼀个根据实际ID⾃动增⻓的IntegerField通常不指定, 如果不指定主键字段id将⾃动添加到模型中。 CharField(max_length字符⻓度) ·字符串默认的表单样式是 Input相当于数据库中的varchar. TextField ·⼤⽂本字段⼀般超过4000使⽤默认的表单控件是Textarea,相当于数据库中的text. IntegerField ·整数 DecimalField(max_digitsNone, decimal_placesNone) ·使⽤python的Decimal实例表示的⼗进制浮点数 ·参数说明 ·DecimalField.max_digits ·位数总数 ·DecimalField.decimal_places ·⼩数点后的数字位数 FloatField
⽤Python的float实例来表示的浮点数
BooleanField
True/False 字段此字段的默认表单控制是CheckboxInput
DateField([auto_nowFalse, auto_now_addFalse])
·使⽤Python的datetime.date实例表示的⽇期
·参数说明
·DateField.auto_now
每次保存对象时⾃动设置该字段为当前时间⽤于最后⼀次修改的时间戳它总是使⽤当前⽇期默认为false。
DateField.auto_now_add
当对象第⼀次被创建时⾃动设置当前时间⽤于创建的时间戳它总是使⽤创建时的⽇期默认为false。
注意auto_now_add, auto_now, and default 这些设置是相互排斥的他们之间的任何组合将会发⽣错误的结果
TimeField
使⽤Python的datetime.time实例表示的时间参数同DateField。
DateTimeField
·使⽤Python的datetime.datetime实例表示的⽇期和时间参数同DateField。 FileField ⼀个上传⽂件的字段 ImageField
继承了FileField的所有属性和⽅法但对上传的对象进⾏校验确保它是个有效的image
需要安装Pillow “pip install Pillow”
字段参数
字段参数写在models.BooleanField()内部。
# 常⽤字段选项通过字段选项可以实现对字段的约束
1、 nullTrue
数据库中字段是否可以为空
2、 blankTrue
django的 Admin 中添加数据时是否可允许空值⼀般nullTrue blankTrue 搭配着⽤出现nullTrue就⽤上blankTrue
3、 primary_key True
主键对AutoField设置主键后就会代替原来的⾃增 id 列
4、 auto_now 和 auto_now_add
auto_now ⾃动创建---⽆论添加或修改都是当前操作的时间
auto_now_add ⾃动创建---永远是创建时的时间5、 choices 后台admin下拉菜单
//限制选择
USER_TYPE_LIST (
(1, 超级⽤户),
(2, 普通⽤户),)user_type models.IntegerField(choicesUSER_TYPE_LIST,
default1, verbose_name⽤户类型)
6、 max_length 最⼤⻓度
7、 default 默认值
8、 verbose_name Admin后台显示的名称中字段的显示名称类似注释
9、 name|db_column 数据库中的字段名称
10、uniqueTrue 不允许重复
11、db_index True 数据库索引,例如如果你想通过name查询的更快的话给他设置为索引即可
12、editableTrue 在Admin⾥是否可编辑不可编辑则不显示
13、设置表名
class Meta:db_table person (表名)案例实战
创建项目工程 数据迁移
python manage.py makemigrations映射数据库
python manage.py migrate注意每对模型进行一次修改都需要重新进行映射。
对于新添加的列最后给一个默认值因为可能前几列的值已经固定了但是我们后面的列没有进行赋值就会存在问题. 后台管理配置 设置管理员
python manage.py createsuperuser后台查看 显示问题
如果想让其显示除需要定义model的魔术方法例如 def __str__(self): # 控制return f{self.id}-{self.name}-{self.age}def __repr__(self):return f{self.id}-{self.name}-{self.age}如何实现回滚操作呢
1.首先删除migrantions中的内容,如下 在数据库中删除 App下的models.py
from django.db import models# 模型 字段类型和约束
class UserModel(models.Model):# uid 会成为主键原来的id不会创建uid models.AutoField(auto_createdTrue, primary_keyTrue)# CharField: 字符串类型unique唯一db_index索引# 名字唯一name models.CharField(max_length30, uniqueTrue, db_indexTrue)# IntegerField: 整数类型default默认值age models.IntegerField(default18)# BooleanField: bool类型sex models.BooleanField(defaultTrue)# # TextField长字符串大文本# nullTrue 表示可以为空blankTrue在Admin管理页面可以为空,一般都是同时写info models.TextField(nullTrue, blankTrue)# # FloatField 小数salary models.FloatField(default100000.345)# DecimalField: 十进制小数# max_digits4最大长度# decimal_places2小数点后是2位money models.DecimalField(max_digits4, decimal_places2, default10.34)# # 日期birthday models.DateField(default2000-03-04)birthday2 models.DateTimeField(auto_nowTrue) # 每一次修改后都会自动修改该时间为最新的修改时间birthday3 models.DateTimeField(auto_now_addTrue) # 第一次添加数据的时候的时间以后不会再修改birthday4 models.DateTimeField(auto_now_addTrue) # 第一次添加数据的时候的时间以后不会再修改# # 文件和图片# 保存图片的二进制 可以为空icon models.FileField(nullTrue, blankTrue, upload_tostatic/uploads)icon2 models.ImageField(nullTrue, blankTrue, upload_tostatic/uploads)## # 其他约束# 元组中第一个参数是我们输入的元素# name 属性表示在数据库中生成的字段名字# db_column 数据库中的字段名称# verbose_name 是在后台管理系统中显示出来的名字# editableTrue 在Admin⾥是否可编辑不可编辑则不显示choices ((1, 青铜), (2, 大师), (3, 王者))user_type models.IntegerField(choiceschoices, default1,nameutype, verbose_name用户类型)user_type2 models.IntegerField(default1, editableFalse,db_columnutype2, verbose_name用户类型2)def __str__(self):return f{self.name} - {self.age} 模型操作
⼀般的数据库操作流程
创建数据库设计表结构和字段连接Mysql数据库并编写数据访问层代码业务逻辑层去调⽤数据访问层执⾏数据库操作
Django通过Model操作数据库不管你数据库的类型是MySql或者SqliteDjango⾃动帮你⽣成相应数据库类型的SQL语句所以不需要关注SQL语句和类型对数据的操作Django帮我们⾃动完成。只要会写Model就可以了。
django使⽤对象关系映射Object Relational Mapping简称ORM框架去操控数据库。
ORM(Object Relational Mapping)对象关系映射是⼀种程序技术⽤于实现⾯向对象编程语⾔⾥不同类型系统的数据之间的转换。
ORM
模型表类结构-表结构对象-表的⼀条数据类属性-表的字段
增删改查
添加
# models基本操作
# 增
1创建对象实例然后调⽤save⽅法obj Author()obj.first_name zhangobj.last_name sanobj.save()
2创建对象并初始化,再调⽤save⽅法:obj Author(first_namezhang, last_namesan) obj.save()
3使⽤create⽅法Author.objects.create(first_nameli, last_namesi)
4使⽤get_or_create⽅法可以防⽌重复Author.objects.get_or_create(first_namezhang, last_namesan)
class PersonModel(models.Model):name models.CharField(max_length30, uniqueTrue)age models.IntegerField(default18)class Meta:# 自定义表名默认是app的名字模型名的小写db_table tb_persondef __str__(self):return f{self.id}-{self.name}-{self.age}def __repr__(self):return f{self.id}-{self.name}-{self.age}
迁移 查看表结构 App下的views.py 提供接口
import mathfrom django.db.models import Max, Min, Sum, Avg, Count
from django.shortcuts import render, HttpResponse# 导入models
from App.models import *# 增加数据
def add_person(request):# 方式1# try:# p PersonModel()# p.name 李四# p.age 44# p.save() # 同步到数据库表中# except Exception as e:# return HttpResponse(添加失败)## return HttpResponse(添加成功!)# 方式2# try:# p PersonModel(name王五, age55)# p.save() # 同步到数据库表中# except Exception as e:# return HttpResponse(添加失败)## return HttpResponse(添加成功!)# 方式3# try:# PersonModel.objects.create(name赵六, age66)# except Exception as e:# return HttpResponse(添加失败)## return HttpResponse(添加成功!)# 方式4# try:# ret PersonModel.objects.get_or_create(name钱七, age77)# print(ret:, ret)# # ret: (PersonModel: PersonModel object (5), True)# # 如果是第一次创建则是True如果已经存在则是False## except Exception as e:# return HttpResponse(添加失败)# 添加多条数据for i in range(21, 51):PersonModel.objects.create(namef武{i}范, agei)return HttpResponse(添加成功!)项目工程下的urls.py 写路由 from django.contrib import admin
from django.urls import pathfrom App.views import *urlpatterns [path(add/, add_person), # 添加数据# path(del/, del_person), # 删除数据# path(update/, update_person), # 修改数据# path(get/, get_person), # 查询数据## # 分页# path(paginate/int:page/, paginate, namepaginate),# path(paginate2/int:page/, paginate2, namepaginate2),path(admin/, admin.site.urls),
]删除
# 删使⽤Queryset的delete⽅法
# 删除指定条件的数据Author.objects.filter(first_namezhang).delete() # 删除所有数据Author.objects.all().delete()注意 objects不能直接调⽤delete⽅法。使⽤模型对象的delete⽅法obj Author.objects.get(id5) obj.delete()views.py
# 删除数据
def del_person(request):# 删除数据:# 1. 先找到要删除的数据# 2. 然后删除try:# 删除一条数据# p PersonModel.objects.first() # 第一条数据# p.delete()# 删除多条数据PersonModel.objects.filter(age__gt15).delete() # age15的多条数据except Exception as e:return HttpResponse(删除失败!)return HttpResponse(删除成功!) 修改
# 改Author.objects.filter(last_namedfdf).update(last_namesan)
模型没有定义update⽅法直接给字段赋值并调⽤save能实现update的功能⽐如obj Author.objects.get(id3) obj.first_name zhang obj.save()
save更新时会更新所有字段。如果只想更新某个字段减少数据库操作可以这么做obj.first_name liobj.save(update_fields[first_name])views.py
# 修改数据
def update_person(request):# 修改数据# 1. 先找到要修改的数据# 2. 然后修改try:# 修改一条数据p PersonModel.objects.first()p.age 666# p.save() # 同步到数据库表中p.save(update_fields[age]) # 指定更新的字段提高更新效率# 修改多条数据# PersonModel.objects.all().update(age100)except Exception as e:return HttpResponse(修改失败)return HttpResponse(修改成功) 查询
# 查
get()获取单条数据Author.objects.get(id123) # 一般对主键或者唯一的如果没有找到符合条件的对象会引发模型类.DoesNotExist异常如果找到多个会引发模型类.MultipleObjectsReturned 异常
first()返回查询集(QuerySet)中的第⼀个对象
last()返回查询集中的最后⼀个对象
count()返回当前查询集中的对象个数
exists()判断查询集中是否有数据如果有数据返回True没有反之
all()获取全部数据集Author.objects.all()
values(): 获取指定列的值可以传多个参数返回包含字典的列表保存了字段名和对应的值Author.objects.all().values(password)
values_list(): 获取指定列的值可以传多个参数返回包含元组列表只保存值Author.objects.all().values_list(password)
进阶操作
# 获取个数
Author.objects.filter(nameseven).count()Author.objects.filter(id gt1) # 获取id⼤于1的值
# select * from Author where id 1Author.objects.filter(id gte1) # 获取id⼤于或等于1的值
# select * from Author where id 1Author.objects.filter(id lt10) # 获取id⼩于10的值
# select * from Author where id 10Author.objects.filter(id lte10) # 获取id⼩于或等于10的值
# select * from Author where id 10Author.objects.filter(id lt10, id gt1) # 获取id⼤于1 且 ⼩于10的值
# select * from Author where id 10 and id 1Author.objects.filter(id in[11, 22, 33]) # 获取id在11、22、33中的数据
# select * from Author where id in (11,22,33)# exclude 除了以外取反
Author.objects.exclude(id in[11, 22, 33]) # not in # select * from Author where id not in (11,22,33)Author.objects.filter(name containsven) # contains和数据库中like语法相同 # select * from Author where name like %ven%
Author.objects.filter(name icontainsven) # icontains⼤⼩写不敏感
Author.objects.filter(name regex^ven) # 正则匹配
Author.objects.filter(name iregex^ven) # 正则匹配,忽略⼤⼩写
Author.objects.filter(age range[10, 20]) # 范围bettwen and# startswithistartswith, endswith, iendswith:
# 以什么开始以什么结束和上⾯⼀样带i的是⼤⼩写不敏感的 其实不带i的也忽略⼤⼩写Author.objects.filter(nameseven).order_by(id) # asc升序 Author.objects.filter(nameseven).order_by(-id) # desc降序
Author.objects.all()[10:20] # 切⽚取所有数据的10条到20条分⻚的时候⽤的到
# 下标从0开始不能为负数, 可以实现分⻚views.py
# 查询数据
def get_person(request):# get(): 得到一个对象(一条数据) 必须获得一条数据# 如果没有找到符合条件的对象会引发模型类.DoesNotExist异常# 如果找到多个会引发模型类.MultipleObjectsReturned 异常p PersonModel.objects.get(id5)# p PersonModel.objects.get(18) # 不可以这样写会报错# p PersonModel.objects.get(pk6) # pk:primary key# p PersonModel.objects.get(age100) # 可以# p PersonModel.objects.get(age100) # 不可以报错MultipleObjectsReturned# # p PersonModel.objects.get(age1000) # 不可以报错DoesNotExist# print(* * 30)# print(p, type(p)) # PersonModel对象# print(p.name, p.age)# print(* * 30)# # all(): 获取所有数据# QuerySet [5-武21范-100, 6-武22范-100, 7-武23范-100, 8-武24范-100, 9-武25范-100, 35-de-100]persons PersonModel.objects.all()print(persons, type(persons))
# # QuerySet 查询集
# # 可以遍历查询集for p in persons:print(p.name, p.age)
#
# # first(): 第一条数据p PersonModel.objects.first()print(p.name, p.age)
#
# # last(): 最后一条数据p PersonModel.objects.last()print(p.name, p.age)return HttpResponse(查询成功!)过滤filter:
# # filter(): 过滤使用最多
# 查询有可能一条 也有可能多条,所以得到的是查询集
# persons PersonModel.objects.filter() # 默认没有条件得到所有数据persons PersonModel.objects.filter(age__gt300) # age300persons PersonModel.objects.filter(age__gte300) # age300persons PersonModel.objects.filter(age__lt300) # age300persons PersonModel.objects.filter(age__lte300) # age300persons PersonModel.objects.filter(age300) # age300# # 查询集可以做链式调用 相当于子查询
# print(persons.filter().filter().all().first())print(type(persons)) # django.db.models.query.QuerySet
# for p in persons:
# print(--- , p.name, p.age)
# #
# print(persons.first())
# print(persons.last())
# print(persons.exists()) # 查询集是否存在数据如果存在则为True否则为False
# print(persons.count()) # 查询集中的数据个数# values() 和 values_list()persons PersonModel.objects.filter().all()print(persons:, persons)print(list(persons):, list(persons)) # 将查询集强制转换成列表# values() : 列表套字典包括字段和值# QuerySet [{name: 武21范, age: 100}, {name: 武22范, age: 50}, {name: 武23范, age: 300# }, {name: 武24范, age: 100}print(persons.values():, persons.values()) # 列表套字典# 指定某个字段print(persons.values(name, age):, persons.values(name, age))# values_list(): 列表套元组, 只有值# QuerySet [(5, 武21范, 100), (6, 武22范, 50), (7, 武23范, 300), (8, 武24范, 100), (9, 武25范, 200), (# 35, de, 600)]print(persons.values_list():, persons.values_list())print(persons.values_list(name, age):, persons.values_list(name, age))# 包含 正则 inprint(- * 60)# filter(): 详细, 类似数据库中的where语句persons PersonModel.objects.filter(age__in[100, 200, 666, 777, 888]) # in# exclude(): 排除取反的意思persons PersonModel.objects.exclude(age__in[100, 200, 666, 777, 888]) # not inpersons PersonModel.objects.filter(age__contains6) # 包含, 模糊查找类似likepersons PersonModel.objects.filter(name__contains3) # 包含, 模糊查找类似likepersons PersonModel.objects.filter(name__icontains3) # 包含, 模糊查找类似like ignore大小写(忽略大小写persons PersonModel.objects.filter(name__regex^wu) # 正则匹配姓武的persons PersonModel.objects.filter(name__iregex^wu) # 正则匹配忽略大小写persons PersonModel.objects.filter(age__range[200, 400]) # 200-400之间两边都包含# 开头和结尾 persons PersonModel.objects.filter(name__startswithwu) # 以wu开头忽略大小写persons PersonModel.objects.filter(name__istartswithwu) # 以wu开头忽略大小写persons PersonModel.objects.filter(name__endswithwu) # 以wu结尾忽略大小写persons PersonModel.objects.filter(name__iendswithwu) # 以wu结尾忽略大小写print(persons)聚合函数
# # 聚合函数max,min,sum# 返回的是字典 {age__max: 600}result PersonModel.objects.aggregate(Max(age)) # 最大值 {age__max: 666}result PersonModel.objects.aggregate(Min(age)) # 最小值 {age__min: 100}result PersonModel.objects.aggregate(Sum(age)) # 求和 {age__sum: 1666}result PersonModel.objects.aggregate(Avg(age)) # 平均值 {age__avg: 333.2}result PersonModel.objects.aggregate(Count(age)) # 计数 {age__count: 5}print(result)排序 # 排序# 默认是按照升序排列 # -字段 表示降序persons PersonModel.objects.all().order_by(age) # 升序persons PersonModel.objects.all().order_by(age, -id) # 先按照age升序如果age相同则按id降序排列persons PersonModel.objects.all().order_by(-age) # 降序print(persons)分页
手动分页
views.py
# 分页功能
# 手动分页
def paginate(request, page1):# 页码page# 每页数量per_pageper_page 10# 分页功能# 数据 【1,2,3,4,5,...,100】# 第几页 数据范围 数据下标范围 切片# page1 1 ~ 10 0 ~ 9 [0 : 10]# page2 11 ~ 20 10 ~ 19 [10 : 20]# page3 21 ~ 30 20 ~ 29 [20 : 30]# page4 31 ~ 40 30 ~ 39 [30 : 40]# ...# pagen [(n-1) * 10 : n * 10]# pagepage [(page-1) * per_page : page * per_page]# 实现分页功能persons PersonModel.objects.all()persons persons[(page-1) * per_page : page * per_page] # 切片# 总页数total PersonModel.objects.count() # 总数据量total_page math.ceil(total / per_page) # 总页数 向上取整因为可能有一部分不到10个pages range(1, total_page1) # 1,2,3,4,5,6,7...data {persons: persons,pages: pages}return render(request, paginate.html, data)
templates下的paginate.html
!DOCTYPE html
html langen
headmeta charsetUTF-8titleTitle/titlestyleul {list-style: none; padding: 0}.btns li {float: left;margin: 5px;}hr {clear: both;}/style
/head
bodyh2分页功能/h2hrul classbtns{% for page in pages %}lia href{% url paginate page %} button{{ page }}/button /a/li{% endfor %}/ulhrul{% for person in persons %}li{{ person.name }} - {{ person.age }}/li{% endfor %}/ul/body
/html当然了还有进行路由绑定 自动分页 # 分页器自动分页
from django.core.paginator import Paginatordef paginate2(request, page1):per_page 10 # 每一页数量all_data PersonModel.objects.all()# 分页器paginator Paginator(all_data, per_page)persons paginator.page(page) # 获取第page页的数据pages paginator.page_range # 页码范围可以遍历data {persons: persons, pages: pages}return render(request, paginate2.html, data) from django.contrib import admin
from django.urls import pathfrom App.views import *urlpatterns [path(add/, add_person), # 添加数据path(del/, del_person), # 删除数据path(update/, update_person), # 修改数据path(get/, get_person), # 查询数据## 分页path(paginate/int:page/, paginate, namepaginate), # 给这个路由函数起一个名字path(paginate2/int:page/, paginate2, namepaginate2),path(admin/, admin.site.urls),
]
templates下的paginate2.
!DOCTYPE html
html langen
headmeta charsetUTF-8titleTitle/titlestyleul {list-style: none; padding: 0}.btns li {float: left;margin: 5px;}hr {clear: both;}/style
/head
bodyh2分页功能/h2hrul classbtns{% for page in pages %}lia href{% url paginate2 page %} button{{ page }}/button /a/li{% endfor %}/ulhrul{% for person in persons %}li{{ person.name }} - {{ person.age }}/li{% endfor %}/ul/body
/html总结
本篇博客深入探讨了Django中的模型基础涵盖了ORM对象关系映射的概念及其在Django中的应用详细介绍了各种字段类型以及常用字段参数的使用方法。通过实战案例的讲解读者将学习如何在Django中使用模型进行数据操作并解答了一些常见问题。此外我们还重点介绍了模型的基本操作包括CURD创建、读取、更新和删除以及分页的实现方法。无论您是初学者还是有一定经验的开发者本文都将为您提供全面而实用的Django模型知识。