Sql - 间接外键

 手机用户2502927665 发布于 2023-02-07 14:45

我对数据库设计有一些疑问.

    这有名字吗?

    这是好习惯吗?

    任何性能考虑?

我有一个用于存储关系的通用表结构.

最近我重构了一些使用这种通用结构而不是直接Fk列的东西,但现在我不确定这是否真的是最好的主意.

原始架构:


 +------------------+       +---------------------+    +----------------------+
 | Book             |       | Note                |    | MetaParent           |
 |------------------|       |---------------------|    |----------------------|
 | Id               |       | Id                  |    | Id                   |
 | NoteId           |       | MetaParentId:(Null) |    | MetaTableId          |
 |                  +-------+                     +----+ KeyValue             |
 |                  |       |                     |    |                      |
 |                  |       |                     |    |                      |
 |                  |       |                     |    |                      |
 |                  |       |                     |    |                      |
 |                  |       |                     |    |                      |
 +------------------+       +---------------------+    +----------------------+

新架构


 +------------------+       +---------------------+    +----------------------+
 | Book             |       | Note                |    | MetaParent           |
 |------------------|       |---------------------|    |----------------------|
 | Id               |       | Id                  |    | Id                   |
 |                  |       | MetaParentId:(Null) |    | MetaTableId          |
 |                  +       +                     +----+ KeyValue             |
 |                  |       |                     |    |                      |
 |                  |       |                     |    |                      |
 |                  |       |                     |    |                      |
 |                  |       |                     |    |                      |
 |                  |       |                     |    |                      |
 +------------------+       +---------------------+    +----------------------+

因此,基本上不是在Book和Note之间建立直接的Fk关系,而是使用MetaTableId/KeyValue列通过MetaParent表建立间接关系.

目前,MetaParent表有大约500k记录,并且事情正在以可接受的方式运行.但是我们每晚都在重建索引.

我担心的是,现在Book和Note之间的关系并不明显.您必须知道一个存在并使用MetaParent表.

还有性能,我不知道在什么时候我们遇到了针对MetaTableId/KeyValue运行太慢的连接问题.看起来你在这个表中添加的查询速度越慢.

1 个回答
  • 您应该始终使用"普通"FOREIGN KEY强制执行参照完整性.

    简而言之,FOREIGN KEYs具有以下优点:

      它们已经在DBMS中实现.

      它们是陈述性的,自我记录的和"显而易见的".

      它们不能被绕过(除非明确禁用或删除).

      他们是对的.

      他们很快.

      它们支持级联引用操作(例如ON DELETE CASCADE).

      DBMS知道数据是相关的,允许它在某些情况下找到更好的查询计划.

      如果您使用的是ORM工具,它可以自动生成对象之间的引用.

    以下是在应用程序代码中强制引用完整性的相应缺点:

      您正在复制已完成的工作.

      这是必要的,可能"深埋"在您的应用程序源代码中,并且更难维护.

      具有错误的单个客户端应用程序可能会破坏参照完整性(并破坏数据).

      您可能在应用程序代码中错误地实现了它们.它从一开始看起来很简单,但在并发环境中,很容易引入竞争条件.

      即使您已正确实现它们,您也可能使用某种形式的锁定来避免竞争条件,这可能比DBMS中内置的特别优化的FK更慢/更低可伸缩性.

      你必须自己实现级联.

      DBMS不知道数据是否相关,这可能产生次优查询计划.

      您可能需要在您选择的ORM工具中进行更多手动操作.


    这有名字吗?

    从来没听说过.我听说过使用"通用FK"这个术语,但这可能并不普遍.

    这是好习惯吗?

    不(见上文).

    任何性能考虑?

    是的(见上文).

    2023-02-07 14:46 回答
撰写答案
今天,你开发时遇到什么问题呢?
立即提问
热门标签
PHP1.CN | 中国最专业的PHP中文社区 | PNG素材下载 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有