M即Models,是连接操作数据库的部分
django默认使用sqlite的数据库
在setting.py里:
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.sqlite3',
'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
}
}
要连接使用mysql数据库,要把上面的注释掉,并把如下代码对应补全信息放到配置文件中,
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'database', #你的数据库名称
'USER': 'root', #你的数据库用户名
'PASSWORD': 'pwd', #你的数据库密码
'HOST': '', #你的数据库主机,留空默认为localhost
'PORT': '3306', #你的数据库端口
}
}
注意几点:1.database即数据库的名字,在mysql连接前该数据库必须已经创建,而上面的sqlite数据库下的db.sqlite3则是项目自动创建
2.另外python3.x版本安装pymysql模块
django默认导入的驱动是MySQLdb(python2.x版本),对python3.x版本有很大问题
所以需要在项目名文件下的__init__
里面写入:
import pymysql
pymysql.install_as_MySQLdb()
如此,问题解决,可以正常开始使用
下面介绍Django自带的ORM(对数据库进行操作):
它是对原生sql语句的一个封装,相比之下有几个优点:
1 ORM使得我们的通用数据库交互变得简单易行,而且完全不用考虑该死的SQL语句。快速开发,由此而来。
2 可以避免一些新手程序猿写sql语句带来的性能问题。
也有缺点:
1 性能有所牺牲,不过现在的各种ORM框架都在尝试各种方法,比如缓存,延迟加载登来减轻这个问题。效果很显著。
2 对于个别复杂查询,ORM仍然力不从心,为了解决这个问题,ORM一般也支持写raw sql。
3 通过QuerySet的query属性查询对应操作的sql语句
下面开始学习Django ORM语法:
一,首先是创建表:
在app下的models.py定义类,形式如下:
class book(models.Model):
name=models.CharField(max_length=20)
price=models.IntegerField()
pub_date=models.DateField()
author=models.CharField(max_length=32,null=False)
1.首先要在配置文件中INSTALLED_APPS
加入app名称
2.定义类必须继承models.Model
3.name,price等是表的字段。如果自己没有创建id主键,django会自动创建
4.models.IntergerFiled等是字段的属性,和sql语句都有对应,还可以加一些比如null=False的参数,详见https://www.cnblogs.com/yuanchenqi/articles/6083427.html
在类写完之后,需要运行加载:
1.终端执行python manage.py makemigrations
正常情况下会 在对应app下的migrations会生成相关py文件
但是django2.x版本的可能遇到一个报错信息:
mysqlclient 1.3.13 or newer is required; you have 0.9.3.
解决方法链接:
https://blog.youkuaiyun.com/weixin_33127753/article/details/89100552
2.终端执行python manage.py migrate
这样之后在django中创建的表就加载到数据库啦
这里再提一个数据库可视化工具,那就是pycharm右边的Database,可以自己试着用,很方便的
二,表的操作
单表操作
1.----------------------增(create , save)---------------------
方法一:
表名.objects.create(字段设置)
方法二:
表名(字段配置).save()
2.------------------------删(delete) ------------------------
表名.objects.filter(筛选条件).delete()
总结就是先把要删的记录找出来,然后删
3.****----------------------改(update和save) --------------------
1.表名.objects.filter(筛选条件).update(字段配置) 推荐!!
说明:<1>filter(**kwargs): 它包含了与所给筛选条件相匹配的对象 返回的是一个QuerySet(django自定义类型),可以用列表索引和切片方法
但是表名.objects.filter(筛选条件).update(字段配置)
报错没有update方法,因为部分取出来就不是QuerySet了。
所以只能用来全部修改,要精确修改,得在筛选条件上下功夫
2.index=表名.objects.filter(筛选条件)[可以用列表方法取部分出来]
index.字段=字段值
index.save
比较:
通过在配置文件中加上日志记录部分可以看到原生sql;
LOGGING = {
'version': 1,
'disable_existing_loggers': False,
'handlers': {
'console':{
'level':'DEBUG',
'class':'logging.StreamHandler',
},
},
'loggers': {
'django.db.backends': {
'handlers': ['console'],
'propagate': True,
'level':'DEBUG',
},
}
}
可以看到Django的save()方法更新了不仅仅是修改列的值,还有更新了所有的列。所以推荐第一种
4.---------------------查(filter,value等) -------------------
查询相关API:
**<1>filter(kwargs): 它包含了与所给筛选条件相匹配的对象
<2>all(): 查询所有结果
<3>get(**kwargs): 返回与所给筛选条件相匹配的对象,返回结果有且只有一个,如果符合筛选条件的对象超过一个或者没有都会抛出错误。
#-----------下面的方法都是对查询的结果再进行处理:比如 objects.filter.values()--------
**# <4>values(*field): 返回一个ValueQuerySet——一个特殊的QuerySet,运行后得到的并不是一系列 model的实例化对象,而是一个可迭代的字典序列
<5>exclude(**kwargs): 它包含了与所给筛选条件不匹配的对象
<6>order_by(*field): 对查询结果排序
<7>reverse(): 对查询结果反向排序
<8>distinct(): 从返回结果中剔除重复纪录
<9>values_list(*field): 它与values()非常相似,它返回的是一个元组序列,values返回的是一个字典序列
<10>count(): 返回数据库中匹配查询(QuerySet)的对象数量。
<11>first(): 返回第一条记录
<12>last(): 返回最后一条记录
<13>exists(): 如果QuerySet包含数据,就返回True,否则返回False。**
单表模糊查询:
#---------------了不起的双下划线(__)之单表条件查询----------------
models.Tb1.objects.filter(id__lt=10, id__gt=1) # 获取id大于1 且 小于10的值
models.Tb1.objects.filter(id__in=[11, 22, 33]) # 获取id等于11、22、33的数据
models.Tb1.objects.exclude(id__in=[11, 22, 33]) # not in
models.Tb1.objects.filter(name__contains=“ven”)
models.Tb1.objects.filter(name__icontains=“ven”) # icontains大小写不敏感
models.Tb1.objects.filter(id__range=[1, 2]) # 范围bettwen and
startswith,istartswith, endswith, iendswith,