将修改后的预排序树遍历模型(嵌套集)放入模型中

将修改后的预排序树遍历模型(嵌套集)放入模型中,第1张

将修改后的预排序树遍历模型(嵌套集)放入模型中

好吧,让我们做一些赏金狩猎;)

步骤0-清理示例:
如前所述,示例数据已损坏,因为它未定义有效的嵌套集。如果您从应用程序中获取了此数据,则应检查插入/删除逻辑。

因此,为了进行测试,我使用了一个经过净化的版本,如下所示:(
这里是MySQL,因为它是第一个)

CREATE TABLE t_categories`(  `id` INTEGER UNSIGNED NOT NULL AUTO_INCREMENT,  `title` VARCHAr(45) NOT NULL,  `lft` INTEGER UNSIGNED NOT NULL,  `rght` INTEGER UNSIGNED NOT NULL,  PRIMARY KEY (`id`));INSERT INTO t_categories (title, lft, rght) VALUES ('Cat 1',1,16);INSERT INTO t_categories (title, lft, rght) VALUES ('Cat 2',2,3);INSERT INTO t_categories (title, lft, rght) VALUES ('Cat 3',4,7);INSERT INTO t_categories (title, lft, rght) VALUES ('Cat 4',5,6);INSERT INTO t_categories (title, lft, rght) VALUES ('Cat 5',8,13);INSERT INTO t_categories (title, lft, rght) VALUES ('Cat 6',9,12);INSERT INTO t_categories (title, lft, rght) VALUES ('Cat 7',10,11);INSERT INTO t_categories (title, lft, rght) VALUES ('Cat 8',14,15);

第1步-让数据库对
嵌套集进行 排序 ,其主要是为了方便将树存储在数据库中而发明的,因为它们使查询子树,父关系以及在这种情况下特别感兴趣的顺序和深度变得非常容易:

SELECt node.title, (COUNT(parent.title) - 1) AS depth FROM t_categories AS node CROSS JOIN t_categories AS parent WHERe node.lft BETWEEN parent.lft AND parent.rght GROUP BY node.title ORDER BY node.lft

这将以整齐的顺序返回您的集合,从根节点开始,并以预定顺序一直到结尾。最重要的是,它将把每个节点的深度添加为正整数,指示节点在根之下的级别(级别0)。对于上述示例数据,结果将是:

title, depth'Cat 1', 0'Cat 2', 1'Cat 3', 1'Cat 4', 2'Cat 5', 1'Cat 6', 2'Cat 7', 3'Cat 8', 1

在代码中:

// Grab ordered data$query = '';$query .= 'SELECt node.title, (COUNT(parent.title) - 1) AS depth';$query .= ' FROM t_categories AS node';$query .= ' CROSS JOIN t_categories AS parent';$query .= ' WHERe node.lft BETWEEN parent.lft AND parent.rght';$query .= ' GROUP BY node.title';$query .= ' ORDER BY node.lft';$result = mysql_query($query);// Build array$tree = array();while ($row = mysql_fetch_assoc($result)) {  $tree[] = $row;}

结果数组将如下所示:

Array(    [0] => Array        ( [title] => Cat 1 [depth] => 0        )    [1] => Array        ( [title] => Cat 2 [depth] => 1        )    ...)

第2步-输出为HTML列表片段:

使用while循环:

// bootstrap loop$result = '';$currDepth = -1;  // -1 to get the outer <ul>while (!empty($tree)) {  $currNode = array_shift($tree);  // Level down?  if ($currNode['depth'] > $currDepth) {    // Yes, open <ul>    $result .= '<ul>';  }  // Level up?  if ($currNode['depth'] < $currDepth) {    // Yes, close n open <ul>    $result .= str_repeat('</ul>', $currDepth - $currNode['depth']);  }  // Always add node  $result .= '<li>' . $currNode['title'] . '</li>';  // Adjust current depth  $currDepth = $currNode['depth'];  // Are we finished?  if (empty($tree)) {    // Yes, close n open <ul>    $result .= str_repeat('</ul>', $currDepth + 1);  }}print $result;

与递归函数的逻辑相同:

function renderTree($tree, $currDepth = -1) {  $currNode = array_shift($tree);  $result = '';  // Going down?  if ($currNode['depth'] > $currDepth) {    // Yes, prepend <ul>    $result .= '<ul>';  }  // Going up?  if ($currNode['depth'] < $currDepth) {    // Yes, close n open <ul>    $result .= str_repeat('</ul>', $currDepth - $currNode['depth']);  }  // Always add the node  $result .= '<li>' . $currNode['title'] . '</li>';  // Anything left?  if (!empty($tree)) {    // Yes, recurse    $result .=  renderTree($tree, $currNode['depth']);  }  else {    // No, close remaining <ul>    $result .= str_repeat('</ul>', $currNode['depth'] + 1);  }  return $result;}print renderTree($tree);

两者都将输出以下结构:

<ul>    <li>Cat 1</li>    <li>        <ul> <li>Cat 2</li> <li>Cat 3</li> <li>     <ul>         <li>Cat 4</li>     </ul> </li> <li>Cat 5</li> <li>     <ul>         <li>Cat 6</li>         <li>  <ul>      <li>Cat 7</li>  </ul>         </li>     </ul> </li> <li>Cat 8</li>        </ul>    </li></ul>

Nitpickers角落:发问者明确要求

<ul>
,但 订购了 无序列表!来…



欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/zaji/5641121.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-12-16
下一篇 2022-12-16

发表评论

登录后才能评论

评论列表(0条)

保存