asp 实现无限级分类的问题 分类算法要解决的问题 在网站建设中,分类算法的应用非常的普遍。在设计一个电子商店时,要涉及到商品分类; 在设计发布系统时,要涉及到栏目或者频道分类;在
设计软件下载这样的程序时,要涉及到
软件的分类;如此等等。可以说,分类是一个很普遍的问题。 1、 分类算法常常表现为树的表示和遍历问题。那么,请问:如果用数据库中的一个 Table 来表达树型分类,应该有几个字段? 2、 如何快速地从这个 Table 恢复出一棵树; 3、 如何判断某个分类是否是另一个分类的子类; 4、 如何查找某个分类的所有产品; 5、 如何生成分类所在的路径。 6、 如何新增分类; 在不限制分类的级数和每级分类的个数时,这些问题并不是可以轻松回答的。本文试图解决 这些问题。 分类的数据结构 我们知道:分类的数据结构实际上是一棵树。在《数据结构》课程中,大家可能学过 Tree 的算法。 由于在网站建设中我们大量使用数据库, 所以我们将从 Tree 在数据库中的存储谈起。 为简化问题,我们假设每个节点只需要保留 Name 这一个信息。我们需要为每个节点编号。编 号的方法有很多种。在数据库中
常用的就是自动编号。这在 Access、SQL Server、Oracle 中都是这样。假设编号字段为 ID。 为了表示某个节点 ID1 是另外一个节点 ID2 的父节点, 我们需要在数据库中再保留一个字段, 说明这个分类是属于哪个节点的儿子。把这个字段取名为 FatherID。如这里的 ID2,其 FatherID 就是 ID1。 这样,我们就得到了分类 Catalog 的数据表定义: Create Table [Catalog]( [ID] [int] NOT NULL, [Name] [nvarchar](50) NOT NULL,
[FatherID] [int] NOT NULL ); 约定:我们约定用-1 作为最上面一层分类的父亲编码。编号为-1 的分类。这是一个虚拟的分 类。它在数据库中没有记录。 如何恢复出一棵树 上面的 Catalog 定义的最大优势,就在于用它可以轻松地恢复出一棵树—分类树。为了更清 楚地展示算法,我们先考虑一个简单的问题:怎样显示某个分类的下一级分类。我们知道, 要查询某个分类 FID 的下一级分类,SQL 语句非常简单: select Name from catalog where FatherID=FID 显示这些类别时,我们简单地用 来做到: <% REM oConn---数据库连接,调用 GetChildren 时已经打开 REM FID-----当前分类的编号 Function GetChildren(oConn,FID) strSQL = "select ID,Name from catalog where FatherID="&;FID set rsCatalog = oConn.Execute(strSQL) %> <% Do while not rsCatalog.Eof %> <%=rsCatalog("Name")%> <% Loop %>
<% rsCatalog.Close End Function %> 现 在 我们 来看 看如 何显示 FID 下的 所有 分类 。这 需 要用 到递 归算 法。我 们 只需 要在 GetChildren 函数中简单地对所
有 ID 进行调用:GetChildren(oConn,Catalog(“ID”))就可 以了。 <% REM oConn---数据库连接,已经打开 REM FID-----当前分类的编号 Function GetChildren(oConn,FID) strSQL = "select Name from catalog where FatherID="&;FID set rsCatalog = oConn.Execute(strSQL) %> <% Do while not rsCatalog.Eof %> <%=rsCatalog("Name")%> <%=GetChildren(oConn,Catalog("ID"))%> <% Loop %> <%
rsCatalog.Close End Function %> 修改后的 GetChildren 就可以完成显示 FID 分类的所有子分类的任务。要显示所有的分类, 只需要如此调用就可以了: <% REM strConn--连接数据库的字符串,请根据情况修改 set oConn = Server.CreateObject("ADODB.Connection") oConn.Open strConn =GetChildren(oConn,-1) oConn.Close %> 如何查找某个分类的所有产品; 现在来解决我们在前面提出的第四个问题。第三个
问题留作习题。我们假设产品的数据表如 下定义: Create Table Product( [ID] [int] NOT NULL, [Name] [nvchar] NOT NULL, [FatherID] [int] NOT NULL ); 其中,ID 是产品的编号,Name 是产品的名称,而 FatherID 是产品所属的分类。 对第四个问题,很容易想到的办法是:先找到这个分类 FID 的所有子类,