准备工作:

  1、在orm操作表单之前需要先修改下django中连接的数据库,默认连接的是SQLit3,这里我们修改成mysql

  2、mysql使用的版本是5.6,已经安装好了,直接连接就可以使用

创建django项目,这里我创建的django使用的是pycharm创建的,其中应用、模板都已经创建好了,不需要我们手动去创建了,因为要连接到mysql数据库,默认不支持mysql连接,我们还需要做一些修改。

  创建需要用到的数据库库文件:

  库名:book_system

  修改django中配置文件settings.py文件:

    

在项目中或者应用中目录的__init__.py文件中添加

import pymysql
pymysql.install_as_MySQLdb()

  到这里初步的设置算是完成了,因为我们要使用orm操作数据库,还需要先设计表格字段类型

  在创建的应用app中的models.py目录中创建类

 

class User(models.Model):
name=models.CharField(max_length=32)
age=models.IntegerField()
# DateField 年月日;DateTimeField 年月日时分秒
register_time=models.DateField()
def __str__(self):
return '对象的名字是:%s'%self.name
# 设计book表
class Book(models.Model):
# 设置title字段为varchar类型
title=models.CharField(max_length=32)
# max_digists设置数字长度最大为8,decimal_places小数位
price=models.DecimalField(max_digits=8,decimal_places=2)
# DateField 年月日;DateTimeField 年月日时分秒;auto_now:每次操作改数据都会自动更新时间;auto_now_add:新增数据的时候会将当前时间自动添加,后续的修改该字段不会自动更新
publish_date=models.DateField(auto_now_add=True)
# 外键关系
publish=models.ForeignKey(to='Publish')
authors=models.ManyToManyField(to='Author') def __str__(self):
return '书籍对象的名字是:%s'%self.title # 设计出版社表
class Publish(models.Model):
name=models.CharField(max_length=32)
addr=models.CharField(max_length=32)
#这里默认EmailField类型在不加载其它模块的情况下就是char类型
email=models.EmailField()
def __str__(self):
return '出版社对象的名字:%s'%self.name
# 设计作者表格
class Author(models.Model):
name=models.CharField(max_length=32)
age=models.IntegerField() authordetail=models.OneToOneField(to='AuthorDetail')
def __str__(self):
return '作者对象的名字:%s'%self.name #作者表的扩展表
class AuthorDetail(models.Model):
phone=models.CharField(max_length=32)
addr=models.CharField(max_length=32)

  执行数据库迁移命令、生成数据库需要的表   

  python3 manage.py makemigrations 将数据库更改记录添加到小本本上(对应应用下migrations文件夹)
  python3 manage.py migrate 将更改同步到数据库(真正的操作数据库)

  执行完成后查看数据:

有一些是我们自己设计的,有些是orm系统自己需要用到的表

注意:数据库创建好了,单独的py文件测试orm操作会报错,需要配置参

导入app应用中的models模块

  • 一、数据操作从创建、删除、修改、查询这四个方面开始

新增数据的两种方式:

新增数据方式1:(基于create方法创建)

    #新增数据,创建表
user_obj=models.User.objects.create(name='jason',age='',register_time='2019-06-12')
print(user_obj.register_time)

 

新增数据方式2:(基于对象绑定的方法创建)

from django.test import TestCase

# Create your tests here.
import os
import sys
import datetime if __name__ == "__main__":
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "test01.settings")
import django
django.setup()
from app01 import models
#新增数据,创建表
# user_obj=models.User.objects.create(name='jason',age='25',register_time='2019-06-12')
# print(user_obj.register_time) user_obj=models.User(name='tank',age='23',register_time=datetime.datetime.now())
user_obj.save()

删除数据的两种方式

# 方式1
res = models.User.objects.filter(name='tank').delete()
print(res)  #删除数据会有返回值
# 方式2
res = models.User.objects.filter(name='jason').first()
res.delete()  #删除数据没有返回值

修改数据两种方式

# 方式1
models.User.objects.filter(name='tank').update(age='18')
# 方式2
res=models.User.objects.filter(name='tank').first()
res.age=20
res.save()

查询数据

    <1> all():           查询所有结果

    res=models.User.objects.all()
print(res) <2> filter(**kwargs): 它包含了与所给筛选条件相匹配的对象
res = models.User.objects.filter(name='tank',age=21)
print(res) #filter内支持多个参数,查询条件只有同时满足才会返回查询结果 <3> get(**kwargs): 返回与所给筛选条件相匹配的对象,返回结果有且只有一个,如果符合筛选条件的对象超过一个或者没有都会抛出错误。(源码就去搂一眼~诠释为何只能是一个对象 <4> exclude(**kwargs): 它包含了与所给筛选条件不匹配的对象
res =models.User.objects.exclude(name='tank')
print(res) #查询返回exclude条件之外的其它数据,通俗点就是取反 <5> order_by(*field): 对查询结果排序('-id')/('price')
  res=models.User.objects.order_by('name')
  print(res)  #order_by内可以不同的字段
  res=models.User.objects.order_by('-name')
  print(res)  #倒叙,效果和reverse一样
    <6> reverse():              对查询结果反向排序 	>>>前面要先有排序才能反向

    <7> count():                返回数据库中匹配查询(QuerySet)的对象数量。
  res=models.User.objects.count()
  print(res)
    <8> first():                返回第一条记录
  res=models.User.objects.all().first()
  print(res)
    <9> last():                返回最后一条记录
  
  res=models.User.objects.all().last()
  print(res)
<10> exists(): 如果QuerySet包含数据,就返回True,否则返回False 
res=models.User.objects.filter(name='test').exists()
print(res) #判断数据是否存在,存放返回true,不存在返回false

<11> values(*field): 返回一个ValueQuerySet——一个特殊的QuerySet,运行后得到的并不是一系列 model的实例化对象,而是一个可迭代的字典序列 

<12> values_list(*field): 它与values()非常相似,它返回的是一个元组序列,values返回的是一个字典序列 

<13> distinct(): 从返回结果中剔除重复纪录

基于双下划线的查询

res=models.User.objects.filter(age__gt=21)
print(res)  # 查询年龄大于21岁
res=models.User.objects.filter(age__lt=21)
print(res)  # 查询年龄小于21岁
age__gte  #大于等于
age__lte  #小于等于 
age__in=[44,22,73]  #年龄是44或22或73,只要有一个满足就返回数据
age__range=[22,44]  #年龄在22——44之间范围内
register_time__year=2019  #register_time这个字段的日期数据中年份是2019的数据打印出来
res=models.User.objects.filter(name__contains='o')
print(res)  #name字段中包含有o字符的值打印出来
name__icontains='E'  #含有E字符的值都打印出来,不区分大小写
name__startswith='t'  #字段中符合指定字符开头的打印出来
name__endswith='n'  #字段中负责指定字符结尾的打印出来
到此单表查询结束
=================================================================

多表查询

  插入数据
  models.Book.objects.create(title='红楼梦',price='66.66',publish_id=1)
  传输数据对象:
  publish_obj=models.Publish.objects.filter(pk=2).first()
  models.Book.objects.create(title='三国演义',price=199.99,publish=publish_obj)
  修改数据
  models.Book.objects.filter(pk=1).update(publish_id=3)
   

  publish_obj = models.Publish.objects.filter(pk=2).first()
  models.Book.objects.filter(pk=1).update(publish=publish_obj)
  对象修改

   book_obj = models.Book.objects.filter(pk=1).first()

   book_obj.publish_id = 3 # 点表中真实存在的字段名

  book_obj.save()

  

  publish_obj = models.Publish.objects.filter(pk=2).first()
  book_obj.publish = publish_obj  # 点orm中字段名 传该字段对应的表的数据对象
  book_obj.save()
  
  删除数据
  
models.Book.objects.filter(pk=1).delete()
  models.Publish.objects.filter(pk=1).delete()
 
  book_obj = models.Book.objects.filter(pk=3).first()
  book_obj.delete()
 多表之间添加关系(数据)
  方法1
  book_obj = models.Book.objects.filter(pk=3).first()
 book_obj.authors.add(1)
   方法2
  author_obj = models.Author.objects.filter(pk=1).first()
  author_obj1 = models.Author.objects.filter(pk=3).first()
  book_obj.authors.add(author_obj,author_obj1)

 修改表关系使用set(),set传递的必须是可迭代对象

   方法1

   book_obj = models.Book.objects.filter(pk=3).first()

   可以传数字和对象,并且支持传多个

  book_obj.authors.set((1,))
  book_obj.authors.set((1,2,3))   方法2
  
author_list = models.Author.objects.all()
  book_obj = models.Book.objects.filter(pk=3).first()
  book_obj.authors.set(author_list)

删除书籍与作者的绑定关系
  方法1
  
book_obj = models.Book.objects.filter(pk=3).first()
  book_obj.authors.remove(1)

  方法2
  book_obj = models.Book.objects.filter(pk=3).first()
  author_list = models.Author.objects.all()
  book_obj.authors.remove(*author_list)  # 需要将queryset打散

清空关系表中的数据clear()
清空的是你当前这个表记录对应的绑定关系
 book_obj = models.Book.objects.filter(pk=3).first()
book_obj.authors.clear() 基于对象的表查询
  正向
    查询书籍是三国演义出版社的邮箱

    book_obj =models.Book.objects.filter(title='三国演义').first()

    print(book_obj.publish.email)
    查询书籍是三国演义的作者的姓名
    
book_obj=models.Book.objects.filter(title='三国演义').first()
    print(book_obj.authors)  # app01.Author.None出现这种情况是打印出的数据不是的单个是多个
    
print(book_obj.authors.all())
    查询作者为‘大猫’的电话号码
    phone_obj=models.Author.objects.filter(name='大猫').first()
    print(phone_obj.authordetail.phone)

  反向
    查询出版社是上海出版社出版的书籍    一对多字段反向查询
    publish_obj = models.Publish.objects.filter(name='东方出版社').first()
    print(publish_obj.book_set) # app01.Book.None
    print(publish_obj.book_set.all())
    查询作者jason写过的所有的书                      多对多字段的反向查询
    author_obj = models.Author.objects.filter(name='jason').first()
    print(author_obj.book_set) # app01.Book.None
    print(author_obj.book_set.all())     查询作者电话号码是110的作者姓名 一对一字段的反向查询
    authordetail_obj = models.AuthorDetail.objects.filter(phone=110).first()
    print(authordetail_obj.author.name)

    
基于双下滑线的查询
  正向
    查询书籍为三国演义的出版社地址
    res = models.Book.objects.filter(title='三国演义').values('publish__addr','title')
    print(res)
    查询书籍为xxx的作者的姓名
    res = models.Book.objects.filter(title='xxx').values("authors__name",'title')
    print(res)
    查询作者为jason的家乡
    res = models.Author.objects.filter(name='jason').values('authordetail__addr')
    print(res)
 
  反向
    查询南方出版社出版的书名
    res = models.Publish.objects.filter(name='南方出版社').values('book__title')
    print(res)
    查询电话号码为120的作者姓名
    res = models.AuthorDetail.objects.filter(phone=120).values('author__name')
    print(res)
    查询作者为jason的写的书的名字
    res = models.Author.objects.filter(name='jason').values('book__title')
    print(res)
    查询书籍为三国演义的作者的电话号码
    res = models.Book.objects.filter(title='三国演义').values('authors__authordetail__phone')
    print(res)
聚合查询  aggregate
  from django.db.models import Max,Min,Count,Sum,Avg
    查询所有书籍的作者个数
    res = models.Book.objects.filter(pk=3).aggregate(count_num=Count('authors'))
    print(res)
    查询所有出版社出版的书的平均价格
    res = models.Publish.objects.aggregate(avg_price=Avg('book__price'))
    print(res) # 4498.636
    统计东方出版社出版的书籍的个数
    res = models.Publish.objects.filter(name='东方出版社').aggregate(count_num=Count('book__id'))
    print(res) 分组查询(group_by) annotate
    统计每个出版社出版的书的平均价格
    res = models.Publish.objects.annotate(avg_price=Avg('book__price')).values('name','avg_price')
    print(res)
    统计每一本书的作者个数
    res = models.Book.objects.annotate(count_num=Count('authors')).values('title','count_num')
    print(res)
    统计出每个出版社卖的最便宜的书的价格
    res = models.Publish.objects.annotate(min_price=Min('book__price')).values('name','min_price')
    print(res)
    查询每个作者出的书的总价格
    res = models.Author.objects.annotate(sum_price=Sum('book__price')).values('name','sum_price')
    print(res)


ORM表单操作的更多相关文章

  1. Django 的ORM 表间操作

    Django之ORM表间操作   之前完成了简单的数据库数据增加操作.这次学习更多的表间操作. 单表操作 增加 方式一 b = Book(title="Python基础", pub ...

  2. Django之form表单操作

    小白必会三板斧 from django.shortcuts import render,HttpResponse,redirect HttpRespone:返回字符串 render:返回html页面 ...

  3. 基于JQuery的前端form表单操作

    Jquery的前端表单操作:     jquery提供了良好的方法封装,在一些基本的操作的时候,能节省很多的麻烦,其中,在具体使用时,form表单的数据提交是最频繁也最常见的前后数据交换方式,所以在前 ...

  4. 【JavaScript】DOM之表单操作

    DOM 表单操作 1.获取表单 获取表单元素 以Document对象中forms属性来获取当前HTML页面所有表单集合以Document对象中表单的name属性值来获取表单元元素 <body&g ...

  5. python -使用Requests库完成Post表单操作

    """ 使用Requests库完成Post表单操作 """ #_*_codingn:utf8 _*_ import requests fro ...

  6. Django之mysql表单操作

    在Django之ORM模型中总结过django下mysql表的创建操作,接下来总结mysql表记录操作,包括表记录的增.删.改.查. 1. 添加表记录 class UserInfo(models.Mo ...

  7. ExtJs 第二章,Ext.form.Basic表单操作

    1.认识Ext.form.Panel表单面板         Ext.form.field.CheckBox 复选框 checkboxfield Ext.form.CheckBoxGroup 复选框组 ...

  8. 关于form与表单操作

    form表单自动提交规则 form表单中只有一个type=text的input,在input中按enter键,会自动提交: form表单中有多个type=text的input,且无type=submi ...

  9. 还没被玩坏的robobrowser(7)——表单操作

    背景 有一些站点是需要登录之后才能抓取内容的,另外做web测试的时候登录是家常便饭. 这一节里我们就以登陆testerhome为例,讲解一下robobrowser中form的操作. 预备知识 get_ ...

随机推荐

  1. Pyecharts-数据可视化模块

    Pyecharts 介绍 数据可视化模块 Echarts是一个由百度开源的数据可视化,凭借着良好的交互性,精巧的图表设计,得到了众多开发者的认可.而Python是一门富有表达力的语言,很适合用于数据处 ...

  2. Parity game POJ - 1733 带权并查集

    #include<iostream> #include<algorithm> #include<cstdio> using namespace std; <& ...

  3. MySql 小表驱动大表

    在了解之前要先了解对应语法 in 与 exist. IN: select * from A where A.id in (select B.id from B) in后的括号的表达式结果要求之输出一列 ...

  4. thinkphp3.2短信群发项目实例

    项目功能是企业给客户群发短信,我就写这么多,也不知道你能不能运行成功,如果有问题可以在QQ上问我:605114821 项目文件SMS_V2.zip下载地址,百度云:http://yun.baidu.c ...

  5. Electron+React+七牛云 实战跨平台桌面应用(最新更新)

    课程资料获取链接:点击这里 前市场上对 Electron 的呼声很高,它几乎是 Web 开发人员开发桌面客户端的唯一途径,很多大厂都使用 Electron 开发自己的原生应用.Electron 天生适 ...

  6. vue keep-alive 遇见 vue-router

    keep-alive 遇见 vue-router ·keep-alive 是Vue内置的一个组件,可以使被包含的组件保留状态,或避免重新渲染 ·routre-view也是一个组件,如果直接被包在kee ...

  7. (1)-Android学习笔记之:初识Android系统架构和项目结构

    Android系统架构 Android程序结构 创建一个Android项目,为初学便于理解,将程序项目结构切换为Project模式,项目结构如下 .gradle和.idea:这两个目录下放的都是And ...

  8. 541-反转字符串 II

    541-反转字符串 II 给定一个字符串和一个整数 k,你需要对从字符串开头算起的每个 2k 个字符的前k个字符进行反转.如果剩余少于 k 个字符,则将剩余的所有全部反转.如果有小于 2k 但大于或等 ...

  9. sqlalchemy_mptt一次调优

    问题背景: 我用sqlalchemy_mptt构建了一个多级分类项目,数据库用了sqlite.随着数据条数越来越多,写入速度逐渐变慢,一棵树的插入甚至需要1分钟,远远不能满足需求 分析思路: 1. 批 ...

  10. 快速搭建一个基于react的项目

    最近在学习react,快速搭建一个基于react的项目 1.创建一个放项目文件夹,用编辑器打开 2.打开集成终端输入命令: npm install -g create-react-app 3. cre ...