mysql如何让两个字段数据都不能重复?
场景
我mysql里有3个表
1.车辆信息表carInfo
字段为:
carID,主键
2.终端信息表terminalID
字段为:
terminalID,主键
3.车辆与终端的中间表car_bind_terminal
carID,外键
terminalID,外键
任务(需求)
现在需要实现车辆与终端的一对一映射,让中间表里的carID和terminalID这两个字段都不能重复,否则添加数据时会失败。
比如,车辆与终端的中间表car_bind_terminal里边有这样一条数据,代表了车辆1号与终端1号的一对一映射。
carID terminalID
1 1
现在我想要插入分别插入3条数据,分别是(1,2)、(2,1)和(2,2)。
carID terminalID
1 1
1 2 插入失败,因为carID与第一条重复了
2 1 插入失败,因为terminalID与第一条重复了
2 2 插入成功,因为carID和terminalID都没有与第一条重复
理想中的最终结果应为:
carID terminalID
1 1
2 2
行动(解决方案)
方案1:从代码层面解决(正确方案)
添加数据时,先检查数据在数据库中是否重复,若没有,则添加这条数据,否则返回添加失败。
缺点:写法太丑,需要对数据库进行两次操作。
方案2:设置成两个唯一索引(正确方案)
思路借鉴了这个网站的一对一的中间关系表的解决方案。
将carID和terminalID设置为两个唯一索引,我这里用的是Navicat。

因为carID和terminalID是外键,本来就是两个一般索引,在这里我们只需要把这两个索引的类型从Normal设置成Unique就好了。
优点:以后业务变更,不再是一对一,可能变成一对多或是多对多,都能灵活更改。
缺点:多了个中间表,索引数也多了。
方案3:删掉中间表,把从表的主键作为主表的外键,并将外键设置成唯一索引(正确方案)
优点:比上个方案少了个中间表,索引也少一半(2变成1)。
缺点:若将来业务变更为多对多,就要大改。
方案4:设置成一个复合唯一索引(错误方案)
不要设置成复合唯一索引,因为它允许其中的部分字段重复。
不要像下图这样设置。

结果
成功解决,我用了方案2,因为改动工作量小。
总结
1.如果删除carInfo表里的1号车,car_bind_terminal里的(1,1)数据也会跟着删除。
2.就mysql来说(别的不清楚),设置外键时会自动添加一个一般索引(Navicat能看到),设置主键时会自动添加一个唯一索引(Navicat看不到,因为主键是特殊的唯一索引)。
3.复合主键允许其中的部分字段重复。比如复合主键(ID,Name),数据可以同时存在(1,张三)和(2,张三)。
参考
[数据库实体、关系(一对一实现方式、一对多实现方式、多对多实现方式)]:
https://blog.csdn.net/leilei7407/article/details/101037295
mysql如何让两个字段数据都不能重复?的更多相关文章
- sql server中如何将两个字段数据合并成一个字段显示(字段与字段添加特殊符号)
之前,我在做统计数据时,需要一个字段显示某月的订单数量和订单金额,要求组合成一个字段,用括号组合. 统计出来的结果大概是这样的,首先我们来创建一些模拟数据 ---创建订单表--- create tab ...
- Mysql中让两个字段不同时相同的方法
有时候我们会遇到这样的一种情况:有一些不同的专业,每个专业中有一些不同的学号,专业+学号能对应到个人.这时,应该如何在数据库中定义列,来保证专业+学号对应的学生的唯一性呢? 把学号定义成唯一(UNIQ ...
- MYSQL,触发器,实现两个表共用ID不重复
前后台没有分开,为了区分前后台用户,所以分表,但是ID不能重复,因为关联了权限表. 这里实现后台用户表使用奇数ID 前台用户表使用偶数ID MYSQL 没有sequence SET @@auto_in ...
- 如何使用MySQL一个表中的字段更新另一个表中字段
[本文出自:https://www.jb51.net/article/150323.htm] 这篇文章主要介绍了如何使用MySQL一个表中的字段更新另一个表中字段,需要的朋友可以参考下 1,修改1列 ...
- 如何将两个字段合成一个字段显示(oracle和sqlserver的区别)
oracle中,如何将两个字段数据合并成一个字段显示,接下来看一下在sql server和pl/sql的区别 sql server中如何合并(用Cast()函数) --1.创建模拟的数据表--- cr ...
- orcl数据库查询重复数据及删除重复数据方法
工作中,发现数据库表中有许多重复的数据,而这个时候老板需要统计表中有多少条数据时(不包含重复数据),只想说一句MMP,库中好几十万数据,肿么办,无奈只能自己在网上找语句,最终成功解救,下面是我一个实验 ...
- mysql的if用法解决同一张数据表里面两个字段是否相等统计数据量。
MySQL的使用用法如下所示:格式:if(Condition,A,B)意义:当Condition为true时,返回A:当Condition为false时,返回B.作用:作为条件语句使用.mysql的i ...
- Mysql 如何查询两个时间段之间的数据?
Mysql 如何查询两个时间段之间的数据?
- JDBC读写MySQL的大字段数据
JDBC读写MySQL的大字段数据 不管你是新手还是老手,大字段数据的操作常常令你感到很头痛.因为大字段有些特殊,不同数据库处理的方式不一样,大字段的操作常常是以流的方式 来处理的.而非一般的字段 ...
随机推荐
- 阿里云服务器ECS Ubuntu18.04 初次使用配置教程(图形界面安装)
最近由于工作需要,要使用服务器测试,就先自已买了个服务器,就在阿里云买了一个,先买了那个叫虚拟主机的,后来发现不是我需要的,所以退了,就先了这个ECS主机.3年.如果购买就上图了.下面直接进入正题. ...
- Idea自定义代码块【学习笔记】
前言 idea有一个自定义代码块的功能,可以自定义代码块,方便以后工作中减少一些重复操作,这里就简单记录一下idea好用的模板吧,现在有一个关于日志的模板,用于写一个ServiceImpl方法的时候, ...
- 详解CopyOnWrite容器及其源码
详解CopyOnWrite容器及其源码 在jave.util.concurrent包下有这样两个类:CopyOnWriteArrayList和CopyOnWriteArraySet.其中利用到了Cop ...
- width、height为auto或者100%的区别
一.规则 1. 某div不设置宽度,那么width默认为auto. 2. 某子元素div的width为100%(或者设置为等于父元素宽度的具体值,比如父元素width为100px,子元素width也设 ...
- 手动发布本地jar包到Nexus私服
1.Nexus配置 1. 在Nexus私服上建立仓库,用于盛放jar包,如名叫3rd_part. 2. 注册用户Nuxus用户,如名叫dev,密码dev_123. 3. 给dev用户分配能访问3rd_ ...
- Girlfreind:1 Vulnhub Walkthrough
靶机链接: https://www.vulnhub.com/entry/me-and-my-girlfriend-1,409/ 主机扫描: HTTP 目录访问,提示无权限,右键源码,提示XXF即可 正 ...
- SecureCRT的下载、安装( 过程非常详细!!值得查看)
SecureCRT的下载.安装( 过程非常详细!!值得查看) 简单介绍下SecureCRT 一.SecureCRT的下载 二.SecureCRT的安装 简单介绍下SecureCRT SecureCRT ...
- 使用JDBC分别利用Statement和PreparedStatement来对MySQL数据库进行简单的增删改查以及SQL注入的原理
一.MySQL数据库的下载及安装 https://www.mysql.com/ 点击DOWNLOADS,拉到页面底部,找到MySQL Community(GPL)Downloads,点击 选择下图中的 ...
- JS简易计算器的实现,以及代码的优化
用JS实现简易计算器 首先创建结构和样式 <!DOCTYPE html> <html lang="en"> <head> <meta ch ...
- MySql学习-2. NavicatforMySQL 与 MySql的对接以及一些操作:
1.连接: 2.数据库的创建: 3.数据库中表的创建: 4.表的设计: 4.1 设计表: 4.2 增加数据(自动递增只是保证唯一值,即使数据删除了也是得前进):