I would like some advice on how to deal with this use case:
I have the following multidimentional test array with unknow depth:
$entries =
[
[
'id' => 'Foo',
'parent' => 'root',
'logic_rules' => []
],
[
'id' => 'Bar',
'parent' => 'root',
'logic_rules' => [],
'children' => [
[
'id' => 'Foobar',
'parent' => 'Bar',
'logic_rules' => [],
'children' => [
[
'id' => 'Foobar2',
'parent' => 'Foobar',
'logic_rules' => [],
'children' => [
[
'id' => 'Foobar3',
'parent' => 'Foobar2',
'logic_rules' => []
]
]
]
]
]
]
]
];
And I try to traverse the array to execute some logic (excluded from the example), with this recursive function:
function traverse(array $entries, array &$result = [])
{
foreach ($entries as $k => $value) {
// If `logic_rules` exists proceed executing the logic
// and store the result in the same `parent -> id` position
if (array_key_exists('logic_rules', $value)) {
$result[$value['parent']][$value['id']]['logic_rules'] = time(); // some logic
}
// Re-loop if is parent
if (array_key_exists('children', $value)) {
traverse($value['children'], $result);
}
}
return $result;
}
The output of traverse($entries)
is:
Array
(
[root] => Array
(
[Foo] => Array
(
[logic_rules] => 1603091236
)
[Bar] => Array
(
[logic_rules] => 1603091236
)
)
[Bar] => Array
(
[Foobar] => Array
(
[logic_rules] => 1603091236
)
)
[Foobar] => Array
(
[Foobar2] => Array
(
[logic_rules] => 1603091236
)
)
[Foobar2] => Array
(
[Foobar3] => Array
(
[logic_rules] => 1603091236
)
)
)
But I expect this:
Array
(
[root] => Array
(
[Foo] => Array
(
[logic_rules] => 1603091236
)
[Bar] => Array
(
[logic_rules] => 1603091236
[Foobar] => Array
(
[logic_rules] => 1603091236
[Foobar2] => Array
(
[logic_rules] => 1603091236
[Foobar3] => Array
(
[logic_rules] => 1603091236
)
)
)
)
)
)
Seems like it's skipping its ancestors. Any advice on this?
The solution is to refer to the results parent
so the following depth will push to it.
Look at this line:
traverse($value['children'], $result[$value['parent']]);
This code will work for you:
function traverse (array $entries, array &$result = []) {
foreach ($entries as $value) {
// add your logical stuff here
$result[$value['parent']][$value['id']] = array(
'logical_rules' => time()
);
if (array_key_exists('children', $value)) {
traverse($value['children'], $result[$value['parent']]);
}
}
return $result;
}