kelemen / recursor

从单级数组或可迭代对象创建递归数组

v1.0.0 2015-04-07 08:23 UTC

This package is auto-updated.

Last update: 2024-09-18 00:28:12 UTC


README

库通过一些递归依赖从单级数组构建递归数组。

####输入数组示例

$categories = [
	1 => [
		'title' => 'Sport',
		'portal' => 'TopSport',
		'parent_id' => null,
	],
	2 => [
		'title' => 'Hockey',
		'portal' => 'TopSport',
		'parent_id' => 1,
	],
	3 => [
		'title' => 'Football',
		'portal' => 'TopSport',
		'parent_id' => 1,
	],
	4 => [
		'title' => 'World',
		'portal' => 'BestNews',
		'parent_id' => null,
	]
];

NodeListRecursor

只有列表(没有子元素的元素)有标题,节点是包含子元素的数组。

use Kelemen\Recursor\NodeListRecursor;

$recursor = new NodeListRecursor($categories, 'title', 'parent_id');
# sets maximal recursion depth
$list->setMaxDepth(3);
# get final recursive array  
$list = $recursor->getList();

# result
array(2) {
  [1] => array(2) {
    [2] => string(6) "Hockey"
    [3] => string(8) "Football"
  }
  [4] => string(5) "World"
}

GroupRecursor

非常有用,可以生成用于表单选择的数组。

use Kelemen\Recursor\GroupRecursor;

$recursor = new GroupRecursor($categories, 'portal', 'title', 'parent_id');
$list = $recursor->getList();

# result
array(2) {
  ["TopSport"] => array(3) {
    [1] => string(5) "Sport"
    [2] => string(7) "- Hockey"
    [3] => string(9) "- Football"
  }
  ["BestNews"] => array(1) {
    [4] => string(5) "World"
  }
}

自定义递归器

你可以创建一个完全符合你需求的递归器。你需要实现3个抽象方法。

# Used as item key in result array
abstract protected function getItemKey($item, $key);

# Get parent key for given item
abstract protected function getParentItemKey($item, $key);

# Returns result item structure as array
abstract protected function getItemData($item, $key, $childrenCount, $level);

每个递归器都可以使用2个钩子方法

# Called after build every item
protected function afterItemHook(&$item);

# Called after build result array
protected function afterAllHook(&$items);

如果你想创建一个在结果中有子元素的自定义递归器,你需要定义 $subKey 类参数。这个参数需要在 getItemData() 方法中作为数组使用。

自定义递归器示例

这个递归器统计递归项的子元素。

namespace Kelemen\Recursor;

class CategoryRecursor extends Recursor
{
	/** @var string			Sub key */
	protected $subKey = 'sub';

	/**
	 * Returns item key
	 * @param $item
	 * @param $key
	 * @return mixed
	 */
	protected function getItemKey($item, $key)
	{
		return $item['id'];
	}

	/**
	 * Returns item parent key
	 * @param $item
	 * @param $key
	 * @return mixed
	 */
	protected function getParentItemKey($item, $key)
	{
		return $item['parent_id'];
	}

	/**
	 * Returns item result data
	 * @param $item
	 * @param $key
	 * @param int $childrenCount
	 * @param int $level
	 * @return array
	 */
	protected function getItemData($item, $key, $childrenCount, $level)
	{
		return [
			'title' => $item['title'],
			'portal_id' => $item['portal_id'],
			'count' => 0,
			$this->subKey => []
		];
	}

	/**
	 * @param array $return
	 */
	public function afterItemHook(&$return)
	{
		$count = count($return['sub']);
		foreach ($return['sub'] as $sub) {
			$count += $sub['count'];
		}
		$return['count'] = $count;
	}
}