如何将URL列表转换为指定结构的嵌套数组?
问题:将URL路径转换为指定结构的嵌套数组
需求说明
给定以下URL字符串集合:
'page1', 'page1/url1', 'page1/url2/suburl1', 'page2/url3', 'page2/url4/suburl2', 'page2/url4/suburl3'
需要转换为如下嵌套数组结构:
Array ( [page1] => Array ( [0] => "url1" [1] => Array ( [url2] => Array ( [0] => "suburl1" ) ) ) [page2] => Array ( [0] => "url3" [1] => Array ( [url4] => Array ( [0] => "suburl2" [1] => "suburl3" ) ) ) )
现有方案的问题
曾参考相关方法,但在当前场景下不适用:URL层级不一致,且当URL为page1这类无斜杠的单层级路径时,会出现字符串键与数组键重复的异常。
现有问题代码示例:
$urls = [ 'page1', 'page1/url1', 'page1/url2/suburl1', 'page2/url3', 'page2/url4/suburl2', 'page2/url4/suburl3' ]; $paths = []; foreach ($urls as $url) { $path_parts = explode('/', $url); $path = [array_pop($path_parts)]; foreach (array_reverse($path_parts) as $path_part) { $path = [$path_part => $path]; } $paths[] = $path; } $tree = call_user_func_array('array_merge_recursive', $paths); print_r($tree);
异常输出片段:
Array ( [0] => page1 [page1] => Array
解决方案
以下代码可实现需求,避免键重复问题:
$urls = [ 'page1', 'page1/url1', 'page1/url2/suburl1', 'page2/url3', 'page2/url4/suburl2', 'page2/url4/suburl3' ]; $tree = []; foreach ($urls as $url) { $parts = explode('/', $url); $current = &$tree; // 处理单层级URL,确保顶层键为数组 if (count($parts) === 1) { $key = $parts[0]; if (!isset($current[$key]) || !is_array($current[$key])) { $current[$key] = []; } continue; } // 处理多层级URL,先定位顶层父键 $parentKey = array_shift($parts); if (!isset($current[$parentKey]) || !is_array($current[$parentKey])) { $current[$parentKey] = []; } $current = &$current[$parentKey]; $lastPart = array_pop($parts); // 遍历中间层级,创建嵌套结构 foreach ($parts as $part) { $exists = false; // 检查当前层级是否已存在对应键的数组 foreach ($current as &$item) { if (is_array($item) && array_key_exists($part, $item)) { $current = &$item[$part]; $exists = true; break; } } unset($item); // 释放引用 if (!$exists) { $newItem = [$part => []]; $current[] = $newItem; $current = &$newItem[$part]; } } // 添加路径最后一段到当前层级 $current[] = $lastPart; } print_r($tree);
代码逻辑说明
- 初始化空数组
$tree作为最终结果容器 - 遍历每个URL,拆分路径为数组
- 单层级URL直接在顶层创建对应数组键,确保其值为数组类型
- 多层级URL先定位顶层父键,确保父键对应值为数组
- 遍历中间路径层级,检查当前层级是否已有对应嵌套数组,不存在则创建并添加到父数组的索引中
- 将路径的最后一段添加到当前层级的数组内
内容的提问来源于stack exchange,提问作者pileup
相关产品推荐
相关产品推荐

