简体   繁体   English

如何在数据库上保存树结构

[英]how to save a tree structure on DB

My Data has chapters and sub-chapters and items any item need to be under a chapter or sub-chapter. 我的数据包含章节和子章节,以及任何需要在章节或子章节下的内容。 the chapters can be in many levels (chapter -> sub chapter -> sub sub chapter ...). 这些章节可以分为多个级别(章节->子章节->子子章节...)。

every chapter has a number, and i need to show the path for every item and chapter. 每个章节都有一个数字,我需要显示每个项目和章节的路径。

example :
---------------------
01 - chapter 1
01.0001 - item 1
01.001 - sub chapter 1
01.001.0001 - item 1
01.001.0002 - item 2
01.002 - sub chapter 2
01.003 - sub chapter 3
01.003.0001 - item 1

i think to save the chapter in one table and the items in another, because items have another properties (price,type...) 我认为将章节保存在一个表中并将项目保存在另一个表中,因为项目具有另一个属性(价格,类型...)

any chapter will have the parent Id. 任何章节都将具有父ID。

any Thoughts? 有什么想法吗?

Storing tree structures in DB systems is not a trivial task. 在数据库系统中存储树结构并非易事。 The first thing which usually come to the mind is the ParentId. 通常首先想到的是ParentId。 This solution is OK if you have small and fixed number of levels. 如果级别较小且固定,则此解决方案是可以的。 The problem is that it is not so trivial to write a query for this type of table. 问题在于,为这种类型的表编写查询并不是那么简单。 You have to make a query recursive (for dynamic number of levels) or you have to write multiple joins (for fixed number of levels). 您必须进行递归查询(针对动态级别),或者必须编写多个联接(针对固定级别的级别)。 I would recommend to use a varchar Path column instead of ParentId column. 我建议使用varchar Path列而不是ParentId列。 Lets see the example: 让我们来看一个例子:

CREATE TABLE Chapters (    
   ID PRIMARY KEY,    
   Path VARCHAR(1000),     
   Title VARCHAR(255) NOT NULL          
);

Data example: 数据示例:

| Id         | Path        | Title           |
|------------|-------------|-----------------|
| 1          |     1/      | Chapter 1       | 
| 2          |     1/2/    | Chapter 1.1     |
| 3          |     1/2/3   | Chapter 1.1.1   |
| 4          |     1/4/    | Chapter 1.2     |
| 5          |     1/4/5   | Chapter 1.2.1   |
| 6          |     1/4/5/6 | Chapter 1.2.1.1 |

Then to query all descendants of Chapter 1 write: 然后查询第1章的所有后代:

SELECT *
FROM Chapters AS c
WHERE c.Path LIKE '1/' || '%';

To select all ancestors of Chapter 1.1.1 write: 要选择第1.1.1章的所有祖先,请写:

SELECT *
FROM Chapters AS c
WHERE '1/2/3/' LIKE c.Path || '%';

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM