`

树型结构数据在数据库基本表中的存储及维护

 
阅读更多

相关讨论连接:
早就想简单说说: 关于树型结构数据的存储及维护http://expert.csdn.net/Expert/TopicView1.asp?id=1677669

树型结构数据的存储采用:
Tree(ID,ParentID,Remark)
如果仅对于存储来讲,无疑是最经济!
但是利用这样的结构,来提供一些基于稍微复杂点的查询的应用表现形式
效率应该说相当低下!
如: 查询某节点的路径等!
如要高效的查询,我们可以在维护数据时下点功夫!
我们以一个树型结构论坛的实现为例:

Tree(ID,ParentID,RootID,OrderID,MaxID,Indent,Title,Content,Remark)
ID: Integer 帖子ID
ParentID: Integer 父贴ID
RootID: Integer 根帖ID
OrderID: Integer 同一个根帖中,帖子顺序ID
MaxID: Integer 用于使新贴在顶部
Indent: Integer 缩进量
Title: Varchar 帖子标题
Content: Varchar 帖子内容
Remark: Varchar 除 ID,ParentID 外的贴子线索

这样的设计只要维护好每一个字段都为查询显示提高了效率!
请看下面的维护程序:
--==========================================
alter procedure AppSP_AddNew
@ID integer
,@Title varchar(8000) =null
,@Content varchar(8000)=null
as
--declare @id int
--set @id=0
if @ID=0
begin
insert into Tree (ParentID,OrderID,Indent,Title,Content)
values (0,0,0,@Title,@Content)
--把帖子顶到上面:
update Tree
set RootID = ID
,MaxId = (select max(id) from Tree)
where RootID is null
end
else
begin
--调整同一个"根帖"中,帖子的内部顺序:
update Tree
set OrderID = OrderID + 1
where RootID = (select rootid
from tree
where ID = @id)
and OrderID > (select OrderID
from Tree
where ID = @id
)
--插入回复的帖子,同时维护 RootID,ParentID,OrderID,Indent,remark,Title,Content
insert into Tree (RootID,ParentID,OrderID,Indent,remark,Title,Content)
select RootID,@ID,OrderID+1,Indent + 1
,case when remark is null then cast(parentid as varchar)
else remark + '-' + cast(parentid as varchar)
end
,isnull(@Title,'Re: ' + Title),@Content
from Tree
where id=@id
--把帖子顶到上面:
update Tree
set maxid = (select max(id)
from Tree
)
where rootid = (select rootid
from tree
where id=@id
)
end
--========================================

该程序用于
1.增加新贴:
AppSP_AddNew 0,'第一个问题','地球是圆的吗?'
2.回复帖子:
AppSP_AddNew 1,'Re: 第一个问题','地球是圆的!'

这样,只需简单查询:
select *, remark + '-' + cast(parentid as varchar) + '-' + cast(id as varchar) , space(indent) + '['
from tree
order by MaxID desc,orderid
就可高效的实现帖子列表及其线索,级别等!
虽然维护时增加了一些工作量!

--相关DDL脚本:
CREATE TABLE [Tree] (
[ID] [int] IDENTITY (1, 1) NOT NULL ,
[ParentID] [int] NULL ,
[RootID] [int] NULL ,
[OrderID] [int] NULL ,
[MaxID] [int] NULL ,
[Indent] [int] NULL ,
[Title] [varchar] (50),
[Content] [varchar] (200) ,
[Remark] [varchar] (250) ,
CONSTRAINT [PK_Tree] PRIMARY KEY CLUSTERED
(
[ID]

相关讨论连接:
早就想简单说说: 关于树型结构数据的存储及维护http://expert.csdn.net/Expert/TopicView1.asp?id=1677669

树型结构数据的存储采用:
Tree(ID,ParentID,Remark)
如果仅对于存储来讲,无疑是最经济!
但是利用这样的结构,来提供一些基于稍微复杂点的查询的应用表现形式
效率应该说相当低下!
如: 查询某节点的路径等!
如要高效的查询,我们可以在维护数据时下点功夫!
我们以一个树型结构论坛的实现为例:

Tree(ID,ParentID,RootID,OrderID,MaxID,Indent,Title,Content,Remark)
ID: Integer 帖子ID
ParentID: Integer 父贴ID
RootID: Integer 根帖ID
OrderID: Integer 同一个根帖中,帖子顺序ID
MaxID: Integer 用于使新贴在顶部
Indent: Integer 缩进量
Title: Varchar 帖子标题
Content: Varchar 帖子内容
Remark: Varchar 除 ID,ParentID 外的贴子线索

这样的设计只要维护好每一个字段都为查询显示提高了效率!
请看下面的维护程序:
--==========================================
alter procedure AppSP_AddNew
@ID integer
,@Title varchar(8000) =null
,@Content varchar(8000)=null
as
--declare @id int
--set @id=0
if @ID=0
begin
insert into Tree (ParentID,OrderID,Indent,Title,Content)
values (0,0,0,@Title,@Content)
--把帖子顶到上面:
update Tree
set RootID = ID
,MaxId = (select max(id) from Tree)
where RootID is null
end
else
begin
--调整同一个"根帖"中,帖子的内部顺序:
update Tree
set OrderID = OrderID + 1
where RootID = (select rootid
from tree
where ID = @id)
and OrderID > (select OrderID
from Tree
where ID = @id
)
--插入回复的帖子,同时维护 RootID,ParentID,OrderID,Indent,remark,Title,Content
insert into Tree (RootID,ParentID,OrderID,Indent,remark,Title,Content)
select RootID,@ID,OrderID+1,Indent + 1
,case when remark is null then cast(parentid as varchar)
else remark + '-' + cast(parentid as varchar)
end
,isnull(@Title,'Re: ' + Title),@Content
from Tree
where id=@id
--把帖子顶到上面:
update Tree
set maxid = (select max(id)
from Tree
)
where rootid = (select rootid
from tree
where id=@id
)
end
--========================================

该程序用于
1.增加新贴:
AppSP_AddNew 0,'第一个问题','地球是圆的吗?'
2.回复帖子:
AppSP_AddNew 1,'Re: 第一个问题','地球是圆的!'

这样,只需简单查询:
select *, remark + '-' + cast(parentid as varchar) + '-' + cast(id as varchar) , space(indent) + '['
from tree
order by MaxID desc,orderid
就可高效的实现帖子列表及其线索,级别等!
虽然维护时增加了一些工作量!

--相关DDL脚本:
CREATE TABLE [Tree] (
[ID] [int] IDENTITY (1, 1) NOT NULL ,
[ParentID] [int] NULL ,
[RootID] [int] NULL ,
[OrderID] [int] NULL ,
[MaxID] [int] NULL ,
[Indent] [int] NULL ,
[Title] [varchar] (50),
[Content] [varchar] (200) ,
[Remark] [varchar] (250) ,
CONSTRAINT [PK_Tree] PRIMARY KEY CLUSTERED
(
[ID]
) ON [PRIMARY]
) ON [PRIMARY]


) ON [PRIMARY]
) ON [PRIMARY]
分享到:
评论

相关推荐

    高校医务收费系统数据库设计说明书

    这些信息由系统管理员管理,存储在数据库表中 5.5输出项 提示信息为信息符号,参考的输出结果如图19,在屏幕上显示一个对话框: 图19:一个显示删除管理员的对话框信息 5.6算法 该窗体主要实现对用户授权,用户的...

    InfoBase 资料管理库

    下班后,在家玩魔兽冰峰王座,过全关一个种族(打了3天),开始写InfoBase的MainMenu (主菜单我一直都没有整理功能,呵呵),Access数据库在删除数据后并不会减少文件尺寸,所以加了几个数据库的维护功能。...

    管理信息系统 试卷 期末试卷

    39.数据库是以一定的组织方式存储在一起的相互有关的数据集合。 数据库管理系统是一组对数据库进行管理的软件。 数据库与传统文件之间的区别是: (1)数据库包含了若干文件,通过联结路径实现记录间的联系。 (2)...

    PHP和MySQL Web开发第4版pdf以及源码

    10.2 在数据库中插入数据 10.3 从数据库中获取数据 10.3.1 获取满足特定条件的数据 10.3.2 从多个表中获取数据 10.3.3 以特定的顺序获取数据 10.3.4 分组与合计数据 10.3.5 选择要返回的行 10.3.6 使用子查询...

    PHP和MySQL WEB开发(第4版)

    10.2 在数据库中插入数据 10.3 从数据库中获取数据 10.3.1 获取满足特定条件的数据 10.3.2 从多个表中获取数据 10.3.3 以特定的顺序获取数据 10.3.4 分组与合计数据 10.3.5 选择要返回的行 10.3.6 使用子查询 10.4 ...

    PHP和MySQL Web开发第4版

    10.2 在数据库中插入数据 10.3 从数据库中获取数据 10.3.1 获取满足特定条件的数据 10.3.2 从多个表中获取数据 10.3.3 以特定的顺序获取数据 10.3.4 分组与合计数据 10.3.5 选择要返回的行 10.3.6 使用子查询...

    Delphi开发范例宝典目录

    实例071 在TListView控件中对数据排序或统计 84 实例072 在TListView组件中绘制底纹 86 实例073 在列表视图中拖动视图项 87 2.6 TTreeView控件应用典型实例 88 实例074 将数据库数据显示到树视图中 88 ...

    软件工程-理论与实践(许家珆)习题答案

    在E-R模型中,包含以下基本成分(C)。 A) 数据、对象、实体 B) 控制、联系、对象 C) 实体、联系、属性 D) 实体、属性、联系 7. 画DFD图的主要目的是(A D)。 A) 作为需求分析阶段用户与开发者之间交流信息的...

    JAVA上百实例源码以及开源项目源代码

    在有状态SessionBean中,用累加器,以对话状态存储起来,创建EJB对象,并将当前的计数器初始化,调用每一个EJB对象的count()方法,保证Bean正常被激活和钝化,EJB对象是用完毕,从内存中清除…… Java Socket 聊天...

    JAVA上百实例源码以及开源项目

    在有状态SessionBean中,用累加器,以对话状态存储起来,创建EJB对象,并将当前的计数器初始化,调用每一个EJB对象的count()方法,保证Bean正常被激活和钝化,EJB对象是用完毕,从内存中清除…… Java Socket 聊天...

Global site tag (gtag.js) - Google Analytics