对Django外键关系的描述


Posted in Python onJuly 26, 2019

注:本文需要你有一定的数据库知识,本文的数据库语法使用mysql书写

Django中,跟外键有关的关系有三种,下面来一一介绍。

OneToManyField

这种最好理解,说白了就是最普通的外键,看看下面两个模型:

class GoodsType(models.Model):
  name = models.CharField(max_length=50)

class GoodsMessage(models.Model):
  Title = models.CharField(max_length='100') # 商品标题
  Category = models.ManyToManyField(GoodsType) # 商品标签

分析一下:

这里Django会在数据库中创两张表:

create table GoodsType(
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(50) NOT NULL,
  PRIMARY KEY (`id`)
)

create table GoodsMessage(
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `Title` varchar(50) NOT NULL,
  `Category_id` int(11) NOT NULL,
  PRIMARY KEY (`id`),
  FOREIGN KEY (`Category_id`) REFERENCES `SchoolBuy_goodstype` (`id`)
)

这样的结果就是一个商品会对应一个类别,即类别是商品的外键。

OneToOneField

这种关系和OneToMany类似,是一种有约束的外键,看看下面两个模型:

class GoodsType(models.Model):
  name = models.CharField(max_length=50)

class GoodsMessage(models.Model):
  Title = models.CharField(max_length='100') # 商品标题
  Category = models.OneToManyField(GoodsType) # 商品标签 (变为一对一关系)

他们会使得数据库创建什么表呢?

create table GoodsType(
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `name` varchar(50) NOT NULL,
  PRIMARY KEY (`id`)
)

create table GoodsMessage(
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `Title` varchar(50) NOT NULL,
  `Category_id` int(11) NOT NULL,
  PRIMARY KEY (`id`),
  FOREIGN KEY (`Category_id`) REFERENCES `SchoolBuy_goodstype` (`id`),
  UNIQUE KEY `SchoolBuy_goodsmessage_Category_id_4dd415fc1e19cf24_uniq` (`Category_id`) # 新增
)

那么这里已经很明显了,在这两个模型里,每个商品有一个商品类型,并且每个商品类型只属于一个商品(用了UNIQUE约束),即如果我A商品的类型是电脑,那么其他商品的类型都不能定义为电脑了。

所以商品与类型的对应关系肯定不能是OneToOne,而应该是OneToMany。

那么OneToOne用在哪里呢?这里说一个地方,在扩展Django的User模型时,因为系统自带的字段不够,所以一种最基本的扩展方法是定义一个User_profile表,用来作为用户的扩展,那么一条用户记录只会有一个扩展表记录,并且这个这个记录也只属于该用户。

ManyToMany

多对多关系,这里我们假设一种情景:

我现在有一个商品表,这个商品有一些图片(不定数量),那么可以使用多对多关系:

class GoodsPicture(models.Model):
  Pic = models.ImageField(upload_to='pic/')

class GoodsMessage(models.Model):
  Title = models.CharField(max_length='100') # 商品标题
  Pic = models.ManyToManyField(GoodsPicture)

这里数据库不同啦,建立了三张表,具体如下:

create table GoodsPicture(
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `Pic` varchar(255) NOT NULL, # Django对于图片的保存采用的是二进制图片文件存硬盘,数据库只保存图片路径
  PRIMARY KEY (`id`)
)

create table GoodsMessage(
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `Title` varchar(50) NOT NULL,
  PRIMARY KEY (`id`)
  # 注意了,这里没有外键约束了
)

create table GoodsMessage_CoodsPicture(
  `id` int(11) NOT NULL AUTO_INCREMENT,
  `goodsmessage_id` int(11) NOT NULL,
  `goodpicture_id` int(11) NOT NULL,
  PRIMARY KEY (`id`),
  UNIQUE KEY `goodsmessage_id` (`goodsmessage_id`,`goodspicture_id`),
  FOREIGN KEY (`goodsmessage_id`) REFERENCES `GoodsMessage` (`id`),
  FOREIGN KEY (`goodstype_id`) REFERENCES `GoodsPicture` (`id`)
)

前两个表就不讲了,主要说一下第三个表GoodsMessage_CoodsPicture,

Django用这个表来记录一条数据,内容为:某个商品对应某张图片。其中有一个UNIQUE约束,说明不能有重复的记录。

这样,每次查询GoodsMessage_CoodsPicture表,就能获得某件商品对应的图片。

这里讲了他们在数据库中的实现,那么Django如何来查询这些数据呢,有一篇好的博文推荐给大家:

以上这篇对Django外键关系的描述就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
深入理解Python中字典的键的使用
Aug 19 Python
Python设置Socket代理及实现远程摄像头控制的例子
Nov 13 Python
python多进程共享变量
Apr 06 Python
Python中easy_install 和 pip 的安装及使用
Jun 05 Python
Python实现查询某个目录下修改时间最新的文件示例
Aug 29 Python
Django csrf 验证问题的实现
Oct 09 Python
Jacobi迭代算法的Python实现详解
Jun 29 Python
python实现大文件分割与合并
Jul 22 Python
Python高级特性——详解多维数组切片(Slice)
Nov 26 Python
Python应用实现双指数函数及拟合代码实例
Jun 19 Python
python openssl模块安装及用法
Dec 06 Python
如何利用python和DOS获取wifi密码
Mar 31 Python
python绘图模块matplotlib示例详解
Jul 26 #Python
详解Python中正则匹配TAB及空格的小技巧
Jul 26 #Python
基于Django ORM、一对一、一对多、多对多的全面讲解
Jul 26 #Python
Django Rest framework频率原理与限制
Jul 26 #Python
Django 使用easy_thumbnails压缩上传的图片方法
Jul 26 #Python
解决django服务器重启端口被占用的问题
Jul 26 #Python
深入解析神经网络从原理到实现
Jul 26 #Python
You might like
PHP下常用正则表达式整理
2010/10/26 PHP
Thinkphp通过一个入口文件如何区分移动端和PC端
2017/04/18 PHP
PHP实现的简单在线计算器功能示例
2017/08/02 PHP
PHP使用mongoclient简单操作mongodb数据库示例
2019/02/08 PHP
一端时间轮换的广告
2006/06/26 Javascript
JavaScript类型转换方法及需要注意的问题小结(挺全面)
2010/11/11 Javascript
JavaScript中的变量声明早于赋值分析
2012/03/01 Javascript
文本框input聚焦失焦样式实现代码
2012/10/12 Javascript
javascript中apply和call方法的作用及区别说明
2014/02/14 Javascript
javascript操作referer详细解析
2014/03/10 Javascript
Jquery 点击按钮自动高亮实现原理及代码
2014/04/25 Javascript
JS图片自动轮换效果实现思路附截图
2014/04/30 Javascript
解析浏览器端的AJAX缓存机制
2016/06/21 Javascript
AngularJS入门教程之Scope(作用域)
2016/07/27 Javascript
webpack搭建vue 项目的步骤
2017/12/27 Javascript
vue中添加mp3音频文件的方法
2018/03/02 Javascript
vue-cli 默认路由再子路由选中下的选中状态问题及解决代码
2018/09/06 Javascript
JS使用new操作符创建对象的方法分析
2019/05/30 Javascript
JS检索下拉列表框中被选项目的索引号(selectedIndex)
2019/12/17 Javascript
AI小程序之语音听写来了,十分钟掌握百度大脑语音听写全攻略
2020/03/13 Javascript
返回上一个url并刷新界面的js代码
2020/09/12 Javascript
基于Python实现的扫雷游戏实例代码
2014/08/01 Python
在Python的Django框架中编写编译函数
2015/07/20 Python
python 爬虫 批量获取代理ip的实例代码
2018/05/22 Python
基于python读取.mat文件并取出信息
2019/12/16 Python
执行Python程序时模块报错问题
2020/03/26 Python
如何用python免费看美剧
2020/08/11 Python
预备党员入党思想汇报
2014/01/04 职场文书
六年级数学教学反思
2014/02/03 职场文书
2014学校庆三八妇女节活动总结
2014/03/01 职场文书
公司合作意向书范文
2014/07/30 职场文书
教师民族团结演讲稿
2014/08/27 职场文书
2014和解协议书范文
2014/09/15 职场文书
创业计划书之情侣餐厅
2019/09/29 职场文书
Python序列化与反序列化相关知识总结
2021/06/08 Python
教你使用VS Code的MySQL扩展管理数据库的方法
2022/01/22 MySQL