To sort an existing multidimensional array I tried to use usort, but it wont bring me any result. As I can not use nested sets or something like this because of the given structure, I have to sort it:
My array:
[
2 => [
'position' => 0,
'children' => [
3 => ['position' => "375"],
5 => ['position' => "44"],
6 => ['position' => "567"],
9 => [
'position' => "12",
'children' => [
74 => ['position' => "2"],
76 => ['position' => "3"],
77 => ['position' => "1"],
]
],
62 => ['position' => "34"],
63 => ['position' => "11"],
66 => ['position' => "114"],
74 => ['position' => "912"],
76 => ['position' => "4564"],
]
]
]
I would like to sort every level by its node named "children". Recursion should be no problem. It can be a variable structure where the node "children" can exist ... or not :)
Desired result after sorting by position
column values:
[
2 => [
'position' => 0,
'children' => [
63 => ['position' => "11"],
9 => [
'position' => "12",
'children' => [
77 => ['position' => "1"],
74 => ['position' => "2"],
76 => ['position' => "3"],
]
],
62 => ['position' => "34"],
5 => ['position' => "44"],
66 => ['position' => "114"],
3 => ['position' => "375"],
6 => ['position' => "567"],
74 => ['position' => "912"],
76 => ['position' => "4564"],
]
]
]
I tried the following code unsuccessfully:
public function recur($data){
// ...
foreach($data as $key=>$value){
if (array_key_exists('children', $value)) {
usort($value, function ($a, $b): int {
if ($a['position'] === $b['position']) {
// ....
}
return $a['position'] <=> $b['position'];
});
}
}
}
CodePudding user response:
Your code does not return any data, so we must assume that your intention is to modify by reference. To implement modification by reference in your recursive method, use the &
symbol in the method's argument signature and the $value
variable of the foreach()
.
The key-preserving sort on the position
column data needs to be done outside of the loop to access the data properly.
After sorting the current row, you can recursively iterate any subset that contains children
data.
Code: (Demo)
function recur(&$data): void
{
uasort($data, fn($a, $b) => $a['position'] <=> $b['position']);
foreach($data as &$value){
if (isset($value['children'])) {
recur($value['children']);
}
}
}
recur($array);
var_export($array);