Mysql刚入门,看到有人说表关联不要用外键约束。
我就有点懵逼了
|  |      1shintendo      2019-09-16 10:55:03 +08:00 说的是不用外键 [约束] ,关联还是那样关联 | 
|  |      2cl903254852 OP @shintendo 是我表达有问题,就是不用外键 | 
|      3littlewing      2019-09-16 10:56:54 +08:00 via iPhone 业务层自己维护 | 
|      4phx13ye      2019-09-16 10:59:03 +08:00  1 代码自己保证呗,然后不做物理删除,美其名为互联网做法 | 
|  |      5mingl0280      2019-09-16 10:59:37 +08:00 业务层维护,好处是数据库服务器可以降低性能需求,坏处是容易弄炸掉关联。 这种说法大部分是超高并发环境(都要减低数据库压力了,得有多少用户啊……),入门别管就可以了。 | 
|  |      6jay0726      2019-09-16 10:59:52 +08:00 不用物理外键而是用逻辑外键 | 
|      7Caballarii      2019-09-16 10:59:57 +08:00 代码里用到的时候约束 一致性完整性自己有空写脚本去对随便怎么都行 数据库上留点没用的数据没什么大不了的 | 
|  |      8love      2019-09-16 11:05:13 +08:00  2 有没有约束和关联查询没有关系。 当然没约束有产生无效 ID 的可能,但对绝大部分应用实际上不是问题。 | 
|  |      9shintendo      2019-09-16 11:19:43 +08:00 @cl903254852  你表达没问题,我就是在回答你的问题 | 
|      10taotaodaddy      2019-09-16 11:23:15 +08:00 via Android 楼主确实要先说清楚是不用物理主键还是连逻辑主键都不用 | 
|      11taotaodaddy      2019-09-16 11:25:21 +08:00 via Android 啊,把“外”敲成“主”了 | 
|  |      12nekolr      2019-09-16 11:37:18 +08:00 就是指建表的时候不建立外键。 使用时还是正常联表查询,和有没有约束时是一样的。再说表之间的关联在逻辑上本来就是存在的,不需要定义。外键约束的作用是维护一致性和完整性,不使用外键,那就只能通过代码层面去保证完整性和一致性。 | 
|      13Raymon111111      2019-09-16 11:40:59 +08:00 一致性业务逻辑去保证 延迟检查补偿最终一致是一种常见的方案 | 
|  |      14leo108      2019-09-16 11:50:50 +08:00 楼上无脑推荐不用外键的,如果外键真这么没用,Mysql 为啥还需要设计这个东西? To 楼主,技术选型要看具体业务,不是阿里说不用外键,整个软件业就都不能用,你要想想别人为什么要这么规定,不用外键带来了什么收益,付出了什么代价,对你自己的业务来说代价和收益哪个更高? | 
|  |      15wysnylc      2019-09-16 11:57:46 +08:00 @leo108 #14 外键带来的问题比解决的问题多,比如要删除 a 表数据但是该表有子表的外键那么就不能删除,这样会导致开发无比的冗余复杂,而在当前的互联网环境下没有这么多时间跟你磨蹭. 严谨和效率从来都是相克的 目前我所知的外键环境只有银行,银行才需要每条数据的精准严谨,所以银行可以放弃效率 但是互联网放弃效率等于百米赛跑你坐轮椅别人一路狂奔甩你 90 米 | 
|  |      16zazalu      2019-09-16 12:02:56 +08:00 楼主是不是一时头晕想糊涂了,就算不使用外键这种"强"约束,也可以通过一些方式来实现“弱”约束从而达到关联的目的,当然这一切都是因为外键貌似影响性能以及纯粹的麻烦!- - | 
|  |      17Vegetable      2019-09-16 12:21:51 +08:00  1 数据库往往是性能瓶颈,所以要给数据库减负,这是大前提. 外键是一个数据库提供的功能,他需要数据库额外的开销对数据合法性进行检查,开销还不小,这就违背了上边说的大前提. 所以这种可以不用数据库做的工作,尽量不用数据库做.不过注意,这么做不是永远正确的. | 
|      18littlewing      2019-09-16 13:18:55 +08:00 @phx13ye 还不是因为互联网穷,用不起 oracle 和 DB2 | 
|  |      19Mosy      2019-09-16 13:20:56 +08:00 via iPhone @wysnylc 大哥,你那里得知的消息银行不需要效率了?银行中间业务系统也不用外键,一天上亿笔交易处理还是需要处理效率的。 | 
|      20lolizeppelin      2019-09-16 13:21:26 +08:00 via Android | 
|  |      21cl903254852 OP @nekolr 你说的对。但是这样的话,ER 图就用不了了,这也是不用数据库外键关联的缺点之一,也是我觉得很可惜的点 | 
|  |      22cl903254852 OP @jay0726 为了性能,牺牲了不少好东西,比如 ER 图 | 
|  |      23cl903254852 OP @wysnylc 赞同 | 
|  |      24cl903254852 OP @zazalu 你说的弱约束一般是指用代码控制吧 | 
|  |      25qiyuey      2019-09-16 13:49:55 +08:00 17 楼说的很对,数据库往往是性能瓶颈,所以使用逻辑外键替代物理外键,并不是说外键的概念有问题,而是实际工程发展出来的解法 | 
|  |      26Mac      2019-09-16 14:10:40 +08:00 via Android 先去搞懂 join 语句的运行逻辑。利用关键字段的关联写业务逻辑就行了。 | 
|  |      28wysnylc      2019-09-16 15:04:44 +08:00 @Mosy #19 不需要效率不代表没有高性能,堆硬件和代码优化同样可以达到高性能 效率是相对的,如果银行不使用外键关联强约束性能会更好,懂了吗? | 
|  |      29younfor      2019-09-16 15:04:48 +08:00 楼主说的大概是数据库层面的物理外键吧。还是看业务场景吧,外键本身设计是在数据库层面实现强一致性和完整性数据约束的。如果你的正确性大于性能的话,可以使用,当然也会有维护成本。不用外键的话,也可以在业务逻辑层用程序代码控制,这个数据会和业务同步修改会有耦合性。 | 
|  |      30wysnylc      2019-09-16 15:05:27 +08:00 @lolizeppelin #20 那银行不敢让你写业务...谁敢这么删数据 | 
|  |      31passerbytiny      2019-09-16 15:09:10 +08:00 @cl903254852  首先,真正的 ER 图是业务模型,它需要先转换成逻辑模型,再转换成物理模型后,才能与数据库扯上关系。 其次,即使是偷懒方式下的 ER 模型,也只需要保证正向工程( ER 图—>数据库结构)时刻可用,不需要保证反向工程总是可用,反向工程只是用来帮助你首次设计 ER 图的时候偷懒的,不是必选项。 | 
|  |      32dog82      2019-09-16 15:10:48 +08:00 在业务层自己写代码控制,不要用 mysql 的外键约束 | 
|      34wangxiaoaer      2019-09-16 15:34:52 +08:00 via Android 想问下你们自己业务层做控制,那么关联查询后分页之类怎么做? 难道业务层两个表全部查出来,然后交叉对比? | 
|  |      35xaplux      2019-09-16 15:42:47 +08:00 只是不用外键约束(比如 MySQL 的外键约束),又没有说不让用外键的那套逻辑,只不过这套逻辑在程序中控制了,ER 图该画的还是要画啊。该怎么表示外键的还是怎么表示就好了 | 
|  |      36shintendo      2019-09-16 15:51:41 +08:00 @wangxiaoaer  在业务层维护约束,不是在业务层 JOIN 啊…… | 
|  |      37wysnylc      2019-09-16 15:53:06 +08:00 @leo108 #33 所以我明说了外键在银行和银行之外的区别,需要严谨的就得抛弃效率拥抱外键,需要效率就抛弃严谨抛弃外键 我打的比方有问题? | 
|  |      39akira      2019-09-16 15:57:41 +08:00 刚入门别看这些 华丽花哨的东西,老老实实把数据库的基础知识概念学好了先。  要不要外键,什么时候要 什么时候不要 这些是生产工作的事情 还不到你接触的时候 | 
|  |      40workspace      2019-09-16 16:08:53 +08:00 users --> id  name age is_del class --> id name is_del class_user --> id class_id user_id is_del # 伪代码 查找用户所在 class class_id = select class_id from class_user where user_id = ${need_query_user_id} and is_del = 0 class = select * from class where id = class_id and is_del = 0 查找 class 中的用户 user_id_list = select user_id from class_user where class_id = ${need_query_class_id} and is_del = 0 user_list = select * from users where id in (user_id_list) and is_del = 0 | 
|      41ralph79      2019-09-16 16:55:32 +08:00 外键时约束,数据自身产生联系就好了,和建不建外键没有关系 | 
|  |      42zazalu      2019-09-16 17:00:03 +08:00 @cl903254852 全部都是软件,全部都是代码,你说的这个代码控制,我觉得说的不太准确哈哈。 控制方式多种多样,随你怎么控制,关键还是在于性能哦!如果你说的这个“代码控制”它本身性能还不如直接用外键,那么又有何意义呢 | 
|  |      43Variazioni      2019-09-16 17:07:21 +08:00 业务层里自己判断啊。。。 | 
|  |      44cl903254852 OP @akira 我看到有人这么说了,就好奇为什么,就过来问问。🤣打扰了打扰了 | 
|  |      45cl903254852 OP @zazalu 大佬说的有道理。我说的代码控制是指 java 或 php 这类的服务端代码根据业务控制外键约束 | 
|      46wangxiaoaer      2019-09-16 17:32:32 +08:00 via Android @shintendo 我艹,我他么傻逼了。不好意思。 | 
|  |      47C02TobNClov1Dz56      2019-09-16 23:20:26 +08:00 数据量大都那么做的吧, 逻辑外键, 业务层控制. 关联表多了, 数据量大了, 物理外键确实会降低并发, 同时, 不方便割接数据, 但是坏处就是容易产生脏数据. | 
|  |      48zomco      2019-09-17 07:06:35 +08:00 via Android 我懵了,表 1 与表 2 不用外键关联的话,是如何用表 1 的第 n 行查询到表第 k,l 行的?是让表 1 冗余,表 1 和表 2 根据 ID 一一对应吗? | 
|      49zc1249274251      2019-09-17 07:25:23 +08:00 设计表的时候,部分冗余,做一些反范式化的设计 | 
|  |      50linxiaojialin      2019-09-17 09:49:48 +08:00 1.用不用外键都可以关联查询; 2.数据的一致性、完整性: 数据量小或者没用分布式的话,可以用外键约束; 数据量大的话,建议在业务层约束; 3.如何判断数据量大小:结合表的记录和实际业务逻辑的复杂度自行判断吧 | 
|  |      51MrYELiex      2019-09-17 10:53:20 +08:00 主要还是因为物理外键在集群上维护性的问题 因为互联网业务场景下数据库大多都是集群 可能用户的一条用户信息在另一台机器上 而他同时下两个订单分别在两个机器上 这怎么维护外键 |