Django ORM深度游:探索多对一、一对一与多对多数据关系的奥秘与实践

系列文章目录
- Django入门全攻略:从零搭建你的第一个Web项目
- Django ORM入门指南:从概念到实践,掌握模型创建、迁移与视图操作
- Django ORM实战:模型字段与元选项配置,以及链式过滤与QF查询详解
- Django ORM深度游:探索多对一、一对一与多对多数据关系的奥秘与实践
- 还在写0.0…
文章目录
- 系列文章目录
- 前言
- 一、多对一关系
- 1.多对一关系是什么
- 2.多对一关系的增删改操作
- 3.多对一的正向查询
- 4.多对一的反向查询
- 二、一对一关系
- 1.一对一关系是什么
- 2.一对一关系的增删改操作
- 3.一对一关系正向查询
- 4.一对一关系反向查询
- 三、多对多关系
- 1.多对多关系是什么
- 2.多对多关系的外键添加操作
- 3.多对多关系的外键移除工作
- 4.多对多关系的修改和查询
前言
在Django开发中,数据关系的管理至关重要。今天,我们将快速了解Django ORM如何处理多对一、一对一和多对多这三种核心数据关系。这些基础知识将帮助你更高效地构建数据库驱动的应用。让我们一起探索Django ORM的奥秘吧!
一、多对一关系
1.多对一关系是什么
Django使用django.db.models.ForeignKey定义多对一关系。
博客表—用户表 - - - 多对一
# app/model.py
class UserModel(models.Model):name = models.CharField(max_length=50)age = models.IntegerField()height = models.DecimalField(max_digits=3, decimal_places=2)def __str__(self):return self.nameclass Meta:db_table = 'users'class BlogModel(models.Model):title = models.CharField(max_length=100)content = models.TextField()pub_date = models.DateField()address = models.CharField(max_length=50)user = models.ForeignKey(to=UserModel, on_delete=models.CASCADE)def __str__(self):return self.titleclass Meta:db_table = 'blogs'
2.多对一关系的增删改操作
增:
# 1.添加useru1 = UserModel.objects.create(name="王五", age=18, height=1.78)# 2.为 id(pk) = 1的用户添加blogu2 = UserModel.objects.get(pk=1)blog = BlogModel()blog.title = "ORM关联模型"blog.content = "多对一、一对一、多对多模型"blog.pub_date = "2024-05-31"blog.address = "csdn"blog.user = u2blog.save()
改:
# 1.修改用户信息# u3 = UserModel.objects.get(id=1)# u3.age = 100# u3.save()# 2.修改博客信息# b3 = BlogModel.objects.get(id=9)# b3.address = "修改后的CSDN地址"b3 = BlogModel.objects.filter(id=9).update(address="再修改(update)后的CSDN地址")# b3.save()
删:
# 1.删除blog表中的记录,直接删除# blog = BlogModel.objects.get(pk=10)# blog.delete()# 2.删除user表中数据,此user对应的blog也会删除u4 = UserModel.objects.get(pk=2)u4.delete()
3.多对一的正向查询
# 多查询一的情况下,直接通过模型类中的外键关联字段查询# 正向查询b5 = BlogModel.objects.get(user_id=1)print(b5)print(b5.user.name)print(b5.user.age)print(b5.user.height)
>>>ORM关联模型
>>>张安
>>>100
>>>1.96
4.多对一的反向查询
# 反向查询:主表通过blogmodel_set查从表u6 = UserModel.objects.get(id=1)print(u6)b6 = u6.blogmodel_set.all()print(b6)for blog in b6:print(blog.title)print(blog.content)
二、一对一关系
1.一对一关系是什么
模型类使用
OneToOneField用来定义一对一关系;
学生表与学生信息表 - - - 一对一
models.CASCADE:多表关联, 删除数据的时候 一删就全删
#app/model.py
class StudentModel(models.Model):name = models.CharField(max_length=50)age = models.IntegerField()height = models.DecimalField(max_digits=3, decimal_places=2)def __str__(self):return self.nameclass Meta:db_table = 'students'class StuDetail(models.Model):address = models.CharField(max_length=50)idcard = models.CharField(max_length=50)outlook = models.CharField(max_length=50)student = models.OneToOneField(to=StudentModel, on_delete=models.CASCADE)def __str__(self):return self.idcardclass Meta:db_table = 'detail'
其中,ON DELETE 和 ON UPDATE 表示事件触发限制,各参数意义如下:
| 参数 | 意义 |
|---|---|
| RESTRICT | 限制外表中的外键改动(默认值,也是最安全的设置) |
| CASCADE | 跟随外键改动 |
| SET NULL | 设为null值 |
| NO ACTION | 无动作 |
| SET DEFAULT | 设为默认值 |
2.一对一关系的增删改操作
增:
# 1.增加学生 Studentst1 = StudentModel()st1.name = "张三三"st1.age = 18st1.height = 1.79st1.save()# 2.增加学生信息 StuDetailsd1 = StuDetail()sd1.address = "北京"sd1.idcard = 123sd1.outlook = '团员'sd1.student = st1sd1.save()
改:
# 3.修改 学生详细信息sd2 = StuDetail.objects.get(id=1)sd2.address = "我在中东吃炸鸡"sd2.save()# 4.修改 学生信息st2 = StudentModel.objects.get(id=1)st2.age = 12st2.save()
删:
# 5.删除st5 = StudentModel.objects.get(id=1)st5.delete()
3.一对一关系正向查询
# 5.正向查询:sd3 = StuDetail.objects.get(id=1)print(sd3.address)print(sd3.idcard)print(sd3.outlook)print(sd3.student.name)print(sd3.student.age)
4.一对一关系反向查询
# 6.反向查询:st4 = StudentModel.objects.get(id=1)print(st4.name)print(st4.age)print(st4.studetail.address)print(st4.studetail.idcard)print(st4.studetail.outlook)#print(stu.blogmodel_set.all())#注意:这是错误的,一对一没有_set,且全通过小写字段(eg:studetail,blogmodel_set)找到类名
三、多对多关系
1.多对多关系是什么
多对多关系在模型中使用
ManyToManyField字段定义
多对多关系可以是具有关联,也可以是没有关联,所以不需要明确指定
on_delete属性
原因:在多对多的情况,有专门的第三张表,存储 对应关系, 表本身并没有字段来存储对应关系,此时删除任意数据,不影响另一张表数据
电影表与演员表 - - - 多对多
# app/models.py
class ActorModel(models.Model):name = models.CharField(max_length=50)age = models.IntegerField()gender = models.CharField(max_length=2)def __str__(self):return self.nameclass Meta:db_table = 'actors'class MovieModel(models.Model):name = models.CharField(max_length=50)mtime = models.CharField(max_length=50)info = models.CharField(max_length=50)actors = models.ManyToManyField(to=ActorModel)def __str__(self):return self.nameclass Meta:db_table = 'movies'
2.多对多关系的外键添加操作
创建:
# 1.添加演员a1 = ActorModel()a1.name = '刘海柱'a1.age = 32a1.gender = '男'a1.save()#a2 = ActorModel()a2.name = '赵小刀'a2.age = 30a2.gender = '女'a2.save()#a3 = ActorModel()a3.name = '哈士奇'a3.age = 33a3.gender = '男'a3.save()-------------------------------------------# 2.添加电影信息m1 = MovieModel()m1.name = "精武门"m1.mtime = "2h"m1.info = "这是一个武打片"m1.save()m2 = MovieModel()m2.name = "ye邪不压正"m2.mtime = "2h30min"m2.info = "这肯呢个肯呢个可能是一个武打片"m2.save()m3 = MovieModel()m3.name = "don东北黑道纷纭"m3.mtime = "2h50min"m3.info = "黄及哦啊哦写"m3.save()
增加:
# 3.给电影添加演员--正向的a1 = ActorModel.objects.get(id=1)a2 = ActorModel.objects.get(id=2)a3 = ActorModel.objects.get(id=3)# 给任意一个电影添加对应的演员m1 = MovieModel.objects.get(id=1)m1.actors.add(a1)m1.actors.add(a2)m1.actors.add(a3)
---------------------------------------------# 4.给演员安排几个电影拍m2 = MovieModel.objects.get(id=2)m3 = MovieModel.objects.get(id=3)a1 = ActorModel.objects.get(id=1)a1.moviemodel_set.add(m2,m3)
3.多对多关系的外键移除工作
多对多关联字段的删除,要使用
remove来进行关系的断开
而不是直接使用delete,remove只会断开数据之间的联系,但是不会将数据删除
# 5.删除,会删除电影及电影-演员表中的对应关系# MovieModel.objects.get(id=1).delete()# 6.删除对应关系:从某电影m6中移除某演员a1,只影响演员-电影对应关系表m6 = MovieModel.objects.get(id=6)a1 = ActorModel.objects.get(id=1)a1.moviemodel_set.remove(m6)
4.多对多关系的修改和查询
# 7.查询数据# 根据任意一个电影,查询所有参演的演员-m1 = MovieModel.objects.get(id=1)print("-"*10)print(m1.actors.all())# 根据任意一个演员,查询拍过的所有电影 f反向查询a1 = ActorModel.objects.get(id=1)print("-"*10)print(a1.moviemodel_set.all())

相关文章:
Django ORM深度游:探索多对一、一对一与多对多数据关系的奥秘与实践
系列文章目录 Django入门全攻略:从零搭建你的第一个Web项目Django ORM入门指南:从概念到实践,掌握模型创建、迁移与视图操作Django ORM实战:模型字段与元选项配置,以及链式过滤与QF查询详解Django ORM深度游ÿ…...
无人机路径规划:基于鸽群优化算法PIO的无人机三维路径规划MATLAB代码
一、无人机模型介绍 无人机三维航迹规划_无人机航迹规划-CSDN博客 二、部分代码 close all clear clc warning (off) global model global gca1 gca2 gca3 gca4 model CreateModel(); % Create search map and parameters load(BestPosition5.mat); load(ConvergenceCurve5…...
ArcGIS属性域和子类型
01 属性域 道路的车道数值是小于10的。在编辑道路的此属性时,为了限制其值在10以内,可以使用属性域。当输入数据超过10时,就会限制输入。 限制输入这个功能是Pro特有的,在ArcMap中输入超出限制的值也是合法的,需要手动…...
电子电器架构 --- 什么是域控制器?
我是穿拖鞋的汉子,魔都中坚持长期主义的汽车电子工程师。 老规矩,分享一段喜欢的文字,避免自己成为高知识低文化的工程师: 屏蔽力是信息过载时代一个人的特殊竞争力,任何消耗你的人和事,多看一眼都是你的不对。非必要不费力证明自己,无利益不试图说服别人,是精神上的节…...
链表头部插入结点
Linked List Inserting a node at beginning #include<stdlib.h>//为了用malloc #include<stdio.h> struct node {int data;struct node* next;//在cpp中可以只写 Node *Link;//为了表意明确,Link也经常被命名为next }; struct node* head…...
k8s集群修改apiserver的ip地址
有时候由于服务器的调整,导致ip的的变化,k8s集群的api大管家的ip变动会导致kubectl的接口都无法正常使用,这是只需要将k8s主节点配置文件的ip替换即可。 例如无需要将原来的192.168.146.202的ip替换成192.168.85.202,执行一下操作…...
C语言编程技巧:深度挖掘与高效实践
C语言编程技巧:深度挖掘与高效实践 在编程的世界里,C语言以其高效、灵活和底层控制能力强等特点,一直备受开发者们的青睐。然而,要想真正掌握C语言的精髓,并编写出高效、健壮的代码,却并非易事。本文将从四…...
十_信号14 - system()
意思是 应在在调用 system() 函数前 阻塞 SIGCHLD 信号,否则,子进程结束的时候,系统会向该进程(父)发送 SIGCHLD信号,则该进程认为是自己的一个子进程结束了,于是调用 wait函数获取子进程的终止状态。这本来是正常的操…...
【Python网络爬虫】详解python爬虫中URL资源抓取
🔗 运行环境:PYTHON 🚩 撰写作者:左手の明天 🥇 精选专栏:《python》 🔥 推荐专栏:《算法研究》 #### 防伪水印——左手の明天 #### 💗 大家好🤗ᾑ…...
AI办公自动化:用kimi批量提取音频中的标题并重命名
很多音频文件,文件名很乱,需要根据音频信息中的标题聪明吗 在kimi中输入提示词: 你是一个Python编程专家,一步步的思考,完成以下脚本的撰写: 打开文件夹:E:\有声\a16z播客 读取里面所有的mp3格…...
flyfish3.0.0配置避坑
1.基础环境准备篇 doc/01-基础环境准备篇.md 云智慧/FlyFish - Gitee.com 使用教程里给出的java环境时,可以显示java版本,但是不能显示Maven的版本 改为: export NODE_HOME/usr/local/node/node-v14.19.3-linux-x64 export PATH$NODE_HOME…...
Spring (33)CSRF(跨站请求伪造)保护
跨站请求伪造(CSRF)是一种常见的网络攻击手段,它允许攻击者在不知情的用户浏览器中发起恶意请求。这种攻击利用了网站对用户浏览器的信任。如果用户在浏览器中已经登录了一个网站,攻击者就可以构造一个请求,这个请求能…...
【一刷《剑指Offer》】面试题 29:数组中出现次数超过一半的数字
力扣对应题目链接:169. 多数元素 - 力扣(LeetCode) 牛客对应题目链接:数组中出现次数超过一半的数字_牛客题霸_牛客网 (nowcoder.com) 核心考点 : 数组使用,简单算法的设计。 一、《剑指Offer》对应内容 二…...
vx小程序初学
小程序初学 在我还没接触到微信小程序之前,通常使用轮播要么手写或使用swiper插件去实现,当我接触到微信小程序之后,我看到了微信小程序的强大之处,让我为大家介绍一下吧! swiper与swiper-item一起使用可以做轮播图 …...
vue 笔记01
目录 01 vuejs中属性的基本使用 02 v-show指令的使用 03 v-if 指令的使用 04 v-for指令的使用 05 v-model 指令 06 template模板标签 07 v-on事件的绑定指令 08 事件中的event对象 01 vuejs中属性的基本使用 {{ }} 叫做mustache模板语法 双花括号 小胡子语法 双花括号…...
开发电商系统的技术选型
开发电商系统是一个复杂的任务,需要全面的技术选型来确保系统的稳定性、可扩展性和性能。本文将详细探讨在开发电商系统时涉及的各方面技术选型,包括架构设计、前端技术、后端技术、数据库选择、缓存策略、安全性、支付系统、日志和监控、以及自动化运维…...
C++STL---vector常见用法
C STL中的vector vector是C标准模板库(STL)中最常用的序列容器之一,它是一个动态数组,能够存储任意类型的对象(如整数、字符串等)。vector的主要优点是提供了快速的随机访问,同时还能够动态地调…...
linux文件共享之samba
1.介绍 Samba是一个开源文件共享服务,可以使linux与windows之间进行文件共享,可以根据不同人员调整共享设置以及权限管理。 2.安装 一个命令就OK了:yum install -y samba [rootansible01 ~]# yum install -y samba 已加载插件:l…...
端午传统食品创意营销方案
端午传统食品创意营销方案 目 录 一、市场营销环境分析 1 (一)历史记载 1 (二)粽叶的象征 1 (三)粽子文化 1 (四)竞争分析 2 (五)粽子当今发展 4 二、产品创…...
制作ChatPDF之Elasticsearch8.13.4搭建(一)
Elasticsearch8.x搭建 在Windows系统上本地安装Elasticsearch的详细步骤如下: 1. 下载Elasticsearch 访问 Elasticsearch下载页面。选择适用于Windows的版本8.13.4,并下载ZIP文件。 2. 解压文件 下载完成后,找到ZIP文件(例如…...
Java 8 Stream API 入门到实践详解
一、告别 for 循环! 传统痛点: Java 8 之前,集合操作离不开冗长的 for 循环和匿名类。例如,过滤列表中的偶数: List<Integer> list Arrays.asList(1, 2, 3, 4, 5); List<Integer> evens new ArrayList…...
《从零掌握MIPI CSI-2: 协议精解与FPGA摄像头开发实战》-- CSI-2 协议详细解析 (一)
CSI-2 协议详细解析 (一) 1. CSI-2层定义(CSI-2 Layer Definitions) 分层结构 :CSI-2协议分为6层: 物理层(PHY Layer) : 定义电气特性、时钟机制和传输介质(导线&#…...
HTML 列表、表格、表单
1 列表标签 作用:布局内容排列整齐的区域 列表分类:无序列表、有序列表、定义列表。 例如: 1.1 无序列表 标签:ul 嵌套 li,ul是无序列表,li是列表条目。 注意事项: ul 标签里面只能包裹 li…...
2025 后端自学UNIAPP【项目实战:旅游项目】6、我的收藏页面
代码框架视图 1、先添加一个获取收藏景点的列表请求 【在文件my_api.js文件中添加】 // 引入公共的请求封装 import http from ./my_http.js// 登录接口(适配服务端返回 Token) export const login async (code, avatar) > {const res await http…...
学校时钟系统,标准考场时钟系统,AI亮相2025高考,赛思时钟系统为教育公平筑起“精准防线”
2025年#高考 将在近日拉开帷幕,#AI 监考一度冲上热搜。当AI深度融入高考,#时间同步 不再是辅助功能,而是决定AI监考系统成败的“生命线”。 AI亮相2025高考,40种异常行为0.5秒精准识别 2025年高考即将拉开帷幕,江西、…...
【C++】纯虚函数类外可以写实现吗?
1. 答案 先说答案,可以。 2.代码测试 .h头文件 #include <iostream> #include <string>// 抽象基类 class AbstractBase { public:AbstractBase() default;virtual ~AbstractBase() default; // 默认析构函数public:virtual int PureVirtualFunct…...
麒麟系统使用-进行.NET开发
文章目录 前言一、搭建dotnet环境1.获取相关资源2.配置dotnet 二、使用dotnet三、其他说明总结 前言 麒麟系统的内核是基于linux的,如果需要进行.NET开发,则需要安装特定的应用。由于NET Framework 是仅适用于 Windows 版本的 .NET,所以要进…...
HTTPS证书一年多少钱?
HTTPS证书作为保障网站数据传输安全的重要工具,成为众多网站运营者的必备选择。然而,面对市场上种类繁多的HTTPS证书,其一年费用究竟是多少,又受哪些因素影响呢? 首先,HTTPS证书通常在PinTrust这样的专业平…...
【笔记】AI Agent 项目 SUNA 部署 之 Docker 构建记录
#工作记录 构建过程记录 Microsoft Windows [Version 10.0.27871.1000] (c) Microsoft Corporation. All rights reserved.(suna-py3.12) F:\PythonProjects\suna>python setup.py --admin███████╗██╗ ██╗███╗ ██╗ █████╗ ██╔════╝…...
Qt学习及使用_第1部分_认识Qt---Qt开发基本流程
前言 学以致用,通过QT框架的学习,一边实践,一边探索编程的方方面面. 参考书:<Qt 6 C开发指南>(以下称"本书") 标识说明:概念用粗体倾斜.重点内容用(加粗黑体)---重点内容(红字)---重点内容(加粗红字), 本书原话内容用深蓝色标识,比较重要的内容用加粗倾…...
