php无限级分类缩进,PHP无限级分类排序输出以及分级缩进思路以及解决方案[修正]...

这篇博客探讨了如何在PHP中实现无限级分类,通过递归和数组操作构建多级目录结构。作者首先展示了初始实现,然后发现了静态变量在递归过程中的问题,导致结果错误。为了解决这个问题,作者改用了全局变量并重新组织了代码。最后,博客提到了一种更简洁的创建分类结构的方法,利用数组引用赋值,提高了效率。

遇到这个问题几天了,终于在所有的同子项目中其它功能都做完之后,决定开始做这个

可以先看看分类结构图

4aec67d9c0d3e16367085934beda70cf.png

其实无限级栏目就像类似的多循环结构,直到最后没有内容循环为止

也就是说,在整个栏目处理中,整个栏目关联就是靠父栏目ID来构造的

所以,我模拟了一个多级分类,如下图,id是栏目id,pid是父栏目ID

$array = array(

1=>0,

2=>1,

3=>2,

7=>1,

4=>0,

5=>4,

6=>5,

);

一个随意模拟的三级目录结构

那么首先我要做的一件事,就是将顶级栏目取出来,然后通过顶级栏目获取到二级栏目

foreach($array as $k=>$v){

if($v==$pid){

$list[] = $k;

}

}

foreach($list as $k=>$v){

$clist[$v] = str_repeat('  ',0);

foreach($array as $k1=>$v1){

if($v1==$v){

$list1[] = $k;

}

}

}

我突然发现,内容居然循环了,也就是说,我如果给循环部定义一个函数,如果这个栏目存在子栏目,那么就调用自己

为了节约整个循环时间,我并不是通过判断是否无法循环退出(貌似也很判断),而是每取出一个栏目,就删除$array的一个键,直到$array为空的时候,自然循环就终止了。

所以,整个代码循环就出来了

/*

* 显示多级栏目表

* @param $array栏目数组结构信息 array(栏目ID=>父栏目ID,)

* @param $pid要搜索的父栏目ID 0为顶级栏目

* @param $strpad间隔字符

* @param $padnum要间隔的字符数量

*/

function keach(&$array,$pid=0,$pad=0,$padnum='++'){

static $clist = array();//定义一个静态数组变量,这样取出来的值可以循环添加键值对

$list = array();//初始化一个数组

foreach($array as $k=>$v){//循环分类数组,找到指定父栏目的栏目ID

if($v==$pid){

$list[] = $k;

unset($array[$k]);//找到后销毁,下一个循环就少一次判断了,直到$array为空

}

}

if(!empty($list)){//如果栏目不为空,也就是这个父栏目下面还有栏目,就要循环自身调取数据

foreach($list as $k=>$v){//以上面获取到的栏目ID为父ID,判断是否存在子栏目

//echo str_repeat($padnum,$pad).$v.'

';

$clist[$v] = str_repeat($padnum,$pad);

keach($array,$v,$pad+2);

}

}

return $clist;

}

最后打印结果

print_r(keach($array,0));

打印出来的结果是:

Array

(

[1] =>

[2] => ++++

[3] => ++++++++

[7] => ++++

[4] =>

[5] => ++++

[6] => ++++++++

)

2天后

终于发现了一个问题,由于要计算目录下所有的子目录,多次调用居然结果一模一样,坑爹的static,在子进程循环中是不能被注销的,而且初始化后就不叫static了,经过左思右想,决定定义一个全局变量,但是每次使用前都初始化一次,万一忘记了呢,所以,出现了下面的代码

/**

* 初始化多级栏目显示,防止递归产生值错误

* @param array $array栏目数组结构信息 array(栏目ID=>父栏目ID,)

* @param string $pid要搜索的父栏目ID 0为顶级栏目

* @param string $pad间隔字符

* @param int $padnum要间隔的字符数量

* @return array()

*/

function keach($array,$pid=0,$pad=0,$padnum='++'){

global $clist;

$clist = array();

return keachdo($array,$pid,$pad);

}

/**

* 显示多级栏目层次表

* @param array $array栏目数组结构信息 array(栏目ID=>父栏目ID,)

* @param string $pid要搜索的父栏目ID 0为顶级栏目

* @param string $pad间隔字符

* @param int $padnum要间隔的字符数量

* @return array()

*/

function keachdo($array,$pid=0,$pad=0,$padnum='++'){

global $clist;

$list = array();

foreach($array as $k=>$v){

if($v==$pid){

$list[] = $k;

unset($array[$k]);

}

}

if(!empty($list)){

foreach($list as $k=>$v){

$clist[$v] = str_repeat($padnum,$pad);

keachdo($array,$v,$pad+1);

}

}

return $clist;

}

八年后(2020年)补充,其实在早几年我就收藏了比较简洁的写法,主要用来生成带有层级关系的多维数组,而我以前写的代码在当前前后端分离的概念下不是很适用。这个写法据说是一位C大神写的,这里放到我的博文下面,巧妙运用数组引用赋值来实现生成分类结构。

function createTree($items) {

$tree = array();

foreach ($items as $item) {

if (isset($items[$item['pid']])){

$items[$item['pid']]['son'][] = &$items[$item['id']];

} else {

$tree[] = &$items[$item['id']];

}

}

return $tree;

}

//生成一个以id为键的数组,数据库读取出来的数据需要预先处理

$items = array(

1=>array('id'=>1,'pid'=>0, 'extend'=>'....'),

2=>array('id'=>2,'pid'=>1, 'extend'=>'....'),

3=>array('id'=>3,'pid'=>2, 'extend'=>'....'),

4=>array('....');

);

createTree($items);

评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符  | 博主筛选后可见
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值