做者:孤独烟
来自:打杂的ZRJhtml
其实这个话题是老生常谈,不少人在工做中确实也不会使用外键。包括在阿里的JAVA规范中也有下面这一条sql
【强制】不得使用外键与级联,一切外键概念必须在应用层解决。 数据库
可是呢,询问他们缘由,大可能是这么回答的服务器
每次作DELETE 或者UPDATE都必须考虑外键约束,会致使开发的时候很痛苦,测试数据极为不方便。并发
坦白说,这么说也是对的。可是呢,不够全面,因此开一文来详细说明。框架
首先咱们明确一点,外键约束是一种约束,这个约束的存在,会保证表间数据的关系“始终完整”。所以,外键约束的存在,并不是全然没有优势。
好比使用外键,能够高并发
保证数据的完整性和一致性性能
级联操做方便测试
将数据完整性判断托付给了数据库完成,减小了程序的代码量code
然而,鱼和熊掌不可兼得。外键是可以保证数据的完整性,可是会给系统带来不少缺陷。正是由于这些缺陷,才致使咱们不推荐使用外键,具体以下
假设一张表名为user_tb。那么这张表里有两个外键字段,指向两张表。那么,每次往user_tb表里插入数据,就必须往两个外键对应的表里查询是否有对应数据。若是交由程序控制,这种查询过程就能够控制在咱们手里,能够省略一些没必要要的查询过程。可是若是由数据库控制,则是必需要去这两张表里判断。
在使用外键的状况下,每次修改数据都须要去另一个表检查数据,须要获取额外的锁。如果在高并发大流量事务场景,使用外键更容易形成死锁。
这里主要是分为两点
作平台迁移方便,好比你从Mysql
迁移到Oracle
,像触发器、外键这种东西,均可以利用框架自己的特性来实现,而不用依赖于数据库自己的特性,作迁移更加方便。
分库分表方便,在水平拆分和分库的状况下,外键是没法生效的。将数据间关系的维护,放入应用程序中,为未来的分库分表省去不少的麻烦。
使用外键,其实将应用程序应该执行的判断逻辑转移到了数据库上。那么这意味着一点,数据库的性能开销变大了,那么这就对DBA的要求就更高了。不少中小型公司因为资金问题,并无聘用专业的DBA,所以他们会选择不用外键,下降数据库的消耗。相反的,若是该约束逻辑在应用程序中,发现应用服务器性能不够,能够加机器,作水平扩展。若是是在数据库服务器上,数据库服务器会成为性能瓶颈,作水平扩展比较困难。