mysql - 使用嵌套集模型时跟踪更改

标签 mysql sql hierarchy nested-sets mysql-5.6

我正在考虑将我的组织层次结构切换为我从 here 收集的嵌套集模型。 。我把它放在 SqlFiddle 中希望能帮助想象它。那里的内容已经简化,有/将会有更多级别,但这应该适合帮助解释。

在我的组织中,教练经常更换。每支球队平均每年会有2-3名新教练,教练在组织中会上下变动,存在很大的波动性。在教练之上,一切几乎都会保持不变,但变化可能/将会发生。

使用我们的旧模型(邻接列表),我们可以通过触发器填充的其他表来跟踪更改,但这个新模型将有新的跟踪要求。我发现我们需要跟踪 rgtlft 数字,以及删除日期和添加日期。此外,我发现在任何给定日期或日期范围“重建”树时会出现一些复杂情况。

我考虑过的两个选择是:

首先,创建一个表来跟踪更改,跟踪 rgtlft 列以及日期值,然后从树中删除教练/团队。我认为这种方式很难“重建”历史查找。

其次,将“已删除”的教练/团队保留在树中,向树中添加一个 bool 值,指示教练/组织是否仍在使用中,并添加一个仅跟踪日期和上一个父级的更改表。这将使历史查找变得更容易(我认为日期范围方面很困难),但会使树变得困惑和膨胀。

哪个选项会更好?我是否缺少一个选项?

我们会经常使用历史查询,但对于一次性查询,所有聚合数据将在第二天按组织级别进行编译和存储。

最佳答案

实际上并不清楚您具体在做什么跟踪和历史查找。不过,我对你的问题有一个一般性的答案。

嵌套集和邻接表模型并不相互排斥。这意味着您可以在表中使用两者,如以下架构所示。

CREATE TABLE `node` (
  `node_id` int(10) unsigned NOT NULL AUTO_INCREMENT,
  `parent_id` int(10) unsigned DEFAULT NULL,
  `l` int(10) unsigned NOT NULL,
  `r` int(10) unsigned NOT NULL,
  `name` varchar(32) NOT NULL,
  PRIMARY KEY (`node_id`),
  KEY `l` (`l`),
  KEY `r` (`r`),
  KEY `parent_id` (`parent_id`),
  CONSTRAINT `node_has_node` FOREIGN KEY (`parent_id`)
    REFERENCES `node` (`node_id`)
    ON DELETE CASCADE
    ON UPDATE CASCADE
) ENGINE=InnoDB;

使用此模式,可以轻松查询子树中的节点并使用 lr 对它们进行计数。同时,使用 node_idparent_id 编写处理直接上升和下降节点的查询也很容易。

因此,我建议您使用嵌套集标记来扩展表格,而无需删除父引用。因此您可以继续使用现有的跟踪逻辑,并具有嵌套集模型的优点。

关于mysql - 使用嵌套集模型时跟踪更改,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25128709/

相关文章:

JAVA类层次结构: Which of the following lines will not compile?

PHP preg_replace 非字母数字导致数据库插入失败

php - 在MySQL数据库中解析多级JSON文件

mysql - 如何撤销sql USE?

java - 为什么我在 Oracle 中得到的出生日期多了一个零?如何更改我的sql?

java - 一次到ArrayList,还是每次到ArrayList?

mysql - SQL VIEW 只返回第一条记录

php - 从一个表(mysql)中获取每个标题并从另一个表中获取url并使用title提取每个url上的数据

sql - 按时间分组记录

d3.js - d3.js 中折叠/伸展树(Splay Tree)的子节点?