Reputation: 4285
I am trying to construct a hierarchy of comments so some have to be nested under each other.
The initial array is something like this:
$comments = [
[
'id'=> 1,
'parent_id'=> null,
'children'=> [],
],
[
'id'=> 2,
'parent_id'=> null,
'children'=> [],
],
[
'id'=> 3,
'parent_id'=> null,
'children'=> [],
],
[
'id'=> 4,
'parent_id'=> 2,
'children'=> [],
],
[
'id'=> 5,
'parent_id'=> 3,
'children'=> [],
],
[
'id'=> 6,
'parent_id'=> 4,
'children'=> [],
],
[
'id'=> 7,
'parent_id'=> 4,
'children'=> [],
],
];
The output for the above array should be something like this:
$comments = [
[
'id'=> 1,
'parent_id'=> null,
'children'=> [],
],
[
'id'=> 2,
'parent_id'=> null,
'children'=> [
[
'id'=> 4,
'parent_id'=> 2,
'children'=> [
[
'id'=> 6,
'parent_id'=> 4,
'children'=> [],
],
[
'id'=> 7,
'parent_id'=> 4,
'children'=> [],
],
],
],
],
],
[
'id'=> 3,
'parent_id'=> null,
'children'=> [
[
'id'=> 5,
'parent_id'=> 3,
'children'=> [],
],
],
],
];
My code below gets the top part right but misses the second level children:
// organize comments into a hierarchy
$tree = array_map(function($comment) use ($comments) {
$children = [];
$comments = array_map(function($child) use ($comment, &$children) {
// return [$child['parent_id'], $comment['id']];
if($child['parent_id'] == $comment['id']){
$children[] = $child;
}
return $child;
}, $comments);
$comment['children'] = $children;
return $comment;
}, $comments);
// remove children from the top
return $comments = array_filter($tree, function($child) {
return !$child['parent_id'];
});
Upvotes: 1
Views: 89
Reputation: 350252
You can use the code posted in this answer (so really this question is a duplicate), but obviously you have to take note of the differences:
null
as opposed to 0 in the referenced answerBecause of the last point you must pass $new[null]
as second argument to createTree
.
Here is the code adapted to your variable names and the above comment taken into account:
$new = array();
foreach ($comments as $a){
$new[$a['parent_id']][] = $a;
}
$tree = createTree($new, $new[null]);
print_r($tree);
function createTree(&$list, $parent){
$tree = array();
foreach ($parent as $k=>$l){
if(isset($list[$l['id']])){
$l['children'] = createTree($list, $list[$l['id']]);
}
$tree[] = $l;
}
return $tree;
}
Upvotes: 1