You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
wkcrm/extend/com/Tree.php

189 lines
6.7 KiB

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

<?php
// +----------------------------------------------------------------------
// | CoreThink [ Simple Efficient Excellent ]
// +----------------------------------------------------------------------
// | Copyright (c) 2014 http://www.corethink.cn All rights reserved.
// +----------------------------------------------------------------------
// | Author: <http://www.corethink.cn>
// +----------------------------------------------------------------------
namespace com;
/**
* 列表树生成工具类
* 该类里的方法一部分来自OneThink一部分来自网络最后加上作者的修改形成完善的Tree类
* @author
*/
class Tree{
/**
* 用于树型数组完成递归格式的全局变量
* @author
*/
private $formatTree;
/**
* 将格式数组转换为基于标题的树(实际还是列表,只是通过在相应字段加前缀实现类似树状结构)
* @param array $list
* @param integer $level 进行递归时传递用的参数
*/
private function _toFormatTree($list, $level = 0, $title = 'label'){
foreach($list as $key=>$val){
$title_prefix = str_repeat("&nbsp;", $level*4);
$val['level'] = $level;
$val['title_show'] = $level == 0 ? $val[$title] : $title_prefix.$val[$title];
if(!array_key_exists('_child', $val)){
array_push($this->formatTree, $val);
}else{
$child = $val['_child'];
unset($val['_child']);
array_push($this->formatTree, $val);
$this->_toFormatTree($child, $level+1, $title); //进行下一层递归
}
}
return;
}
/**
* 将格式数组转换为树
* @param array $list
* @param integer $level 进行递归时传递用的参数
*/
public function toFormatTree($list, $title = 'title', $pk='id', $pid = 'pid', $root = 0, $strict = true){
$list = $this->list_to_tree($list, $pk, $pid, '_child', $root, $strict);
$this->formatTree = array();
$this->_toFormatTree($list, 0, $title);
return $this->formatTree;
}
/**
* 将数据集转换成Tree真正的Tree结构
* @param array $list 要转换的数据集
* @param string $pk ID标记字段
* @param string $pid parent标记字段
* @param string $child 子代key名称
* @param string $root 返回的根节点ID
* @param string $strict 默认严格模式
* @param array $filter 要剔除掉的字段
* @return array
*/
public function list_to_tree($list, $pk='id', $pid = 'pid', $child = 'child', $root = 0, $strict = true,$filter = array()){
// 创建Tree
$tree = array();
if(is_array($list)){
// 创建基于主键的数组引用
$refer = array();
foreach($list as $key => $data){
$refer[$data[$pk]] =& $list[$key];
}
foreach($list as $key => $data){
// 判断是否存在parent
$parent_id = $data[$pid];
if($parent_id === null || (int)$root === (int)$parent_id){
$tree[] =& $list[$key];
}else{
if(isset($refer[$parent_id])){
$parent =& $refer[$parent_id];
$parent['children'][] =& $list[$key];
}else{
if($strict === false){
$tree[] =& $list[$key];
}
}
}
}
//剔除数据
if(count($filter) > 0){
foreach($refer as $key => $data){
foreach ($data as $k => $v) {
if(in_array($k, $filter)) unset($refer[$key][$k]);
}
}
}
}
return $tree;
}
/**
* 将list_to_tree的树还原成列表
* @param array $tree 原来的树
* @param string $child 孩子节点的键
* @param string $order 排序显示的键,一般是主键 升序排列
* @param array $list 过渡用的中间数组,
* @return array 返回排过序的列表数组
*/
public function tree_to_list($tree, $child = '_child', $order='id', &$list = array()){
if(is_array($tree)){
foreach ($tree as $key => $value){
$reffer = $value;
if(isset($reffer[$child])){
unset($reffer[$child]);
tree_to_list($value[$child], $child, $order, $list);
}
$list[] = $reffer;
}
$list = $this->list_sort_by($list, $order, $sortby='asc');
}
return $list;
}
/**
* 对查询结果集进行排序
* @access public
* @param array $list 查询结果
* @param string $field 排序的字段名
* @param array $sortby 排序类型 asc正向排序 desc逆向排序 nat自然排序
* @return array
*/
public function list_sort_by($list,$field, $sortby='asc'){
if(is_array($list)){
$refer = $resultSet = array();
foreach($list as $i => $data)
$refer[$i] = &$data[$field];
switch($sortby){
case 'asc': // 正向排序
asort($refer);
break;
case 'desc':// 逆向排序
arsort($refer);
break;
case 'nat': // 自然排序
natcasesort($refer);
break;
}
foreach ($refer as $key=> $val)
$resultSet[] = &$list[$key];
return $resultSet;
}
return false;
}
/**
* 在数据列表中搜索
* @access public
* @param array $list 数据列表
* @param mixed $condition 查询条件
* 支持 array('name'=>$value) 或者 name=$value
* @return array
*/
function list_search($list,$condition){
if(is_string($condition))
parse_str($condition, $condition);
//返回的结果集合
$resultSet = array();
foreach ($list as $key => $data){
$find = false;
foreach ($condition as $field=>$value){
if(isset($data[$field])){
if(0 === strpos($value,'/')){
$find = preg_match($value,$data[$field]);
}elseif($data[$field]==$value){
$find = true;
}
}
}
if($find){
$resultSet[] = &$list[$key];
}
}
return $resultSet;
}
}