【问题标题】:Database Structure for Tree Data Structure [closed]树数据结构的数据库结构
【发布时间】:2010-10-30 10:10:08
【问题描述】:

在数据库中实现可定制的树数据结构(即具有未知层数的树结构)的最佳方法是什么?

在使用具有自身外键的表之前,我已经这样做了一次。

您还能看到哪些其他实现,这种实现有意义吗?

【问题讨论】:

标签: sql database-design tree


【解决方案1】:

您提到了最常用的实现,即邻接表: https://blogs.msdn.microsoft.com/mvpawardprogram/2012/06/25/hierarchies-convert-adjacency-list-to-nested-sets

还有其他模型,包括物化路径和嵌套集: http://communities.bmc.com/communities/docs/DOC-9902

Joe Celko 写了一本关于这个主题的书,从一般 SQL 的角度来看,这是一本很好的参考书(在上面的嵌套集文章链接中提到过)。

此外,Itzik Ben-Gann 在他的“Microsoft SQL Server 2005 内部:T-SQL 查询”一书中对最常见的选项进行了很好的概述。

选择模型时要考虑的主要事项是:

1) 结构变化频率 - 树的实际结构变化的频率。一些模型提供了更好的结构更新特性。然而,将结构更改与其他数据更改分开很重要。例如,您可能想要为公司的组织结构图建模。有些人会将其建模为邻接列表,使用员工 ID 将员工链接到他们的主管。这通常是次优方法。一种通常效果更好的方法是将组织结构与员工本身分开建模,并将员工作为结构的一个属性进行维护。这样,当员工离开公司时,组织结构本身不需要改变,只需要与离职员工的关联。

2) 树是写重还是读重 - 一些结构在读取结构时工作得很好,但在写入结构时会产生额外的开销。

3) 您需要从结构中获取哪些类型的信息 - 一些结构擅长提供有关结构的某些类型的信息。示例包括查找节点及其所有子节点、查找节点及其所有父节点、查找满足特定条件的子节点的计数等。您需要知道从结构中需要哪些信息来确定最适合的结构你的需求。

【讨论】:

  • 嗨,我正面临问题中所述的完全相同的问题,并想就上述主题向您提问。考虑到第一个主题中的结构(在同一个表中引用 ParentId 的组织结构表(非员工结构)),我需要设置谁是某个区域的老板。我将直接分配该特定区域的所有员工。你会把那个特定区域的老板放在哪里?在同一区域或上面的一个组内?我的方法是让他/她参考上面的小组,这给了我一个更好的结构。谢谢。
  • 第一个链接好像坏了。
【解决方案2】:

看看Managing Hierarchical Data in MySQL。它讨论了在关系数据库中存储和管理分层(树状)数据的两种方法。

第一种方法是邻接列表模型,这就是您所描述的:具有引用表本身的外键。虽然这种方法很简单,但对于某些查询(例如构建整棵树)来说效率可能非常低。

文章中讨论的第二种方法是嵌套集模型。这种方法更加有效和灵活。详细解释和示例查询请参阅文章。

【讨论】:

    【解决方案3】:

    如果您必须使用关系数据库来组织树形数据结构,那么 Postgresql 有很酷的 ltree 模块,它提供数据类型来表示存储在分层树状结构中的数据标签。你可以从那里得到这个想法。(有关更多信息,请参阅:http://www.postgresql.org/docs/9.0/static/ltree.html

    通常 LDAP 用于按层次结构组织记录。

    【讨论】:

      【解决方案4】:

      对我来说,拥有一个带有外键的表确实很有意义。

      然后您可以使用 SQL 中的公用表表达式或 Oracle 中的 connect by prior 语句来构建您的树。

      【讨论】:

      • 我有一个日志表,其中包含一个 LogID 标识列,以及一个带有 FK 的 ParentLogID 列,该 FK 指向 LogID 列。当事务中的第一个日志行被写入时,我抓取 SCOPE_IDENTITY()。所有其他日志记录都使用 ParentLogID 列中的此值写入。这对于将属于一起的行分组非常有用。这是查看发生了什么的唯一真实方法,如果没有这个,它将是来自多个事务的大量日志行混合在一起。
      • @KM - 他说“确实有道理”而不是“没有道理”
      【解决方案5】:

      如果有人使用 MS SQL Server 2008 及更高版本 提出这个问题:SQL Server 2008 及更高版本具有专门为此任务设计的新“hierarchyId”功能。

      更多信息https://docs.microsoft.com/en-us/sql/relational-databases/hierarchical-data-sql-server

      【讨论】:

        猜你喜欢
        • 2010-10-30
        • 2011-03-17
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-05-18
        • 1970-01-01
        相关资源
        最近更新 更多