邻接列表树 - 如何防止循环引用?

时间:2011-02-20 11:14:41

标签: sql mysql circular-reference adjacency-list

我在ID和ParentID的数据库中有一个邻接列表来表示树结构:

-a
--b
---c
-d
--e

当然在记录中,ParentID永远不应该与ID相同,但我还必须阻止循环引用以防止无限循环。这些循环引用理论上可涉及2个以上的记录。 (a-> b,b-> c,c-> a等)

对于每条记录,我将路径存储在字符串列中,如下所示:

a    a
b    a/b
c    a/b/c
d    d
e    d/e

我现在的问题是: 插入/更新时,有没有办法检查是否会出现循环引用?

我应该补充一点,我知道所有关于嵌套集模型等等。我选择了存储路径的邻接方法,因为我觉得它更直观。我使用了触发器和一个单独的路径表,它就像一个魅力,除了可能的循环引用。

2 个答案:

答案 0 :(得分:1)

如果你存储这样的路径,你可以检查路径是否包含id。

答案 1 :(得分:0)

如果您使用的是Oracle,则可以使用CONNECT BY语法实现对周期的检查。节点数应该等于根节点的后代数。

CHECK (
(SELECT COUNT(*) Nodes
 FROM Tree) =
(SELECT COUNT(*) Decendents
 FROM Tree
 START WITH parent_node IS NULL -- Root Node
 CONNECT BY parent_node = PRIOR child_node))

注意,您仍需要其他检查来强制执行树。 IE

具有null的单根节点。 节点可以只有一个父节点。

您无法使用子查询创建检查约束,因此需要转到视图或触发器。