按子数组计数对多维数组进行排序


Sorting multi-dimensional array by count of subarray

我有这样的数组:

Array
(
  [28748] => stdClass Object
    (
        [uid] => 28748
        [status] => 1
        [children] => Array
            (
                [29163] => stdClass Object
                    (
                        [uid] => 29163
                        [status] => 1
                    )
            )
    )
[28708] => stdClass Object
    (
        [uid] => 28708
        [status] => 1
        [children] => Array
            (
                [27104] => stdClass Object
                    (
                        [uid] => 27104
                        [status] => 1
                        [children] => Array
                            (
                                [28250] => stdClass Object
                                    (
                                        [uid] => 28250
                                        [status] => 1
                                    )
                            )
                    )
                [29448] => stdClass Object
                    (
                        [uid] => 29448
                        [status] => 1
                        [children] => Array
                            (
                                [28528] => stdClass Object
                                    (
                                        [uid] => 28528
                                        [status] => 1
                                    )
                                [28329] => stdClass Object
                                    (
                                        [uid] => 28329
                                        [status] => 1
                                        [children] => Array
                                            (
                                                [28533] => stdClass Object
                                                   (
                                                  [uid] => 28533
                                                  [status] => 1
                                               )
                                    )
                                [26548] => stdClass Object
                                    (
                                        [uid] => 26548
                                        [status] => 1
                                     )
                            )
                    )
            )
    )

)

我想根据子数组的数量对数组进行排序,所以子数组的数目越大,就会排在第一位。维度的级别是无限的。在我的情况下,我想成为这个阵列:

Array
(
[28708] => stdClass Object
    (
        [uid] => 28708
        [status] => 1
        [children] => Array
            (
                [29448] => stdClass Object
                    (
                        [uid] => 29448
                        [status] => 1
                        [children] => Array
                            (
                                [28329] => stdClass Object
                                    (
                                        [uid] => 28329
                                        [status] => 1
                                        [children] => Array
                                            (
                                                [28533] => stdClass Object
                                                   (
                                                  [uid] => 28533
                                                  [status] => 1
                                               )
                                    )
                                [28528] => stdClass Object
                                    (
                                        [uid] => 28528
                                        [status] => 1
                                    )
                                [26548] => stdClass Object
                                    (
                                        [uid] => 26548
                                        [status] => 1
                                     )
                            )
                    )
                    [27104] => stdClass Object
                    (
                        [uid] => 27104
                        [status] => 1
                        [children] => Array
                            (
                                [28250] => stdClass Object
                                    (
                                        [uid] => 28250
                                        [status] => 1
                                    )
                            )
                    )
            )
    )
[28748] => stdClass Object
    (
        [uid] => 28748
        [status] => 1
        [children] => Array
            (
                [29163] => stdClass Object
                    (
                        [uid] => 29163
                        [status] => 1
                    )
            )
    )

)

这是我正在检查的新阵列:

Array
(
 [27104] => stdClass Object
    (
        [uid] => 27104
        [status] => 1
        [children] => Array
            (
            [28250] => stdClass Object
                    (
                        [uid] => 28250
                        [status] => 1
                        [children] => Array
                            (
                                [28839] => stdClass Object
                                    (
                                        [uid] => 28839
                                        [status] => 1
                                        [children] => Array
                                            (
                                                [27102] => stdClass Object
                                                    (
                                                        [uid] => 27102
                                                        [status] => 1
                                                    )
                                            )
                                    )
                            )
                    )
                [26551] => stdClass Object
                    (
                        [uid] => 26551
                        [status] => 1
                        [children] => Array
                            (
                                [25368] => stdClass Object
                                    (
                                        [uid] => 25368
                                        [status] => 1
                                    )                            
                            )
                    )
            )
    )
[28708] => stdClass Object
    (
        [uid] => 28708
        [status] => 1
        [children] => Array
            (
                [29448] => stdClass Object
                    (
                        [uid] => 29448
                        [status] => 1
                        [children] => Array
                            (
                                [28528] => stdClass Object
                                    (
                                        [uid] => 28528
                                        [status] => 1
                                    )
                                [28329] => stdClass Object
                                    (
                                        [uid] => 28329
                                        [status] => 1
                                        [children] => Array
                                            (
                                                [28654] => stdClass Object
                                                    (
                                                        [uid] => 28654
                                                        [status] => 1
                                                    )
                                            )
                                    )
                                [26548] => stdClass Object
                                    (
                                        [uid] => 26548
                                        [status] => 1
                                    )
                            )
                    )
            )
    )
[28748] => stdClass Object
    (
        [uid] => 28748
        [status] => 1
        [children] => Array
            (
                [28838] => stdClass Object
                    (
                        [uid] => 28838
                        [status] => 1 
                    )
                [28685] => stdClass Object
                    (
                        [uid] => 28685
                        [status] => 1
                    )
                [29163] => stdClass Object
                    (
                        [uid] => 29163
                        [status] => 1
                    )
            )
    )
  )

在使用"sortByNumChildren($data)"后,我得到了

  Array
 (
  [28748] => stdClass Object
    (
        [uid] => 28748
        [status] => 1
        [children] => Array
            (
                [29163] => stdClass Object
                    (
                        [uid] => 29163
                        [status] => 1
                    )
                [28685] => stdClass Object
                    (
                        [uid] => 28685
                        [status] => 1
                    )
                [28838] => stdClass Object
                    (
                        [uid] => 28838
                        [status] => 1
                    )
            )
    )
[28708] => stdClass Object
    (
        [uid] => 28708
        [status] => 1
        [children] => Array
            (
                [29448] => stdClass Object
                    (
                        [uid] => 29448
                        [status] => 1
                        [children] => Array
                            (
                                [26548] => stdClass Object
                                    (
                                        [uid] => 26548
                                        [status] => 1
                                    )
                                [28329] => stdClass Object
                                    (
                                        [uid] => 28329
                                        [status] => 1
                                        [children] => Array
                                            (
                                                [28654] => stdClass Object
                                                    (
                                                        [uid] => 28654
                                                        [status] => 1
                                                    )
                                            )
                                    )
                                [28528] => stdClass Object
                                    (
                                        [uid] => 28528
                                        [status] => 1
                                    )
                           )
                    )
            )
    )
[27104] => stdClass Object
    (
        [uid] => 27104
        [status] => 1
        [children] => Array
            (
                [26551] => stdClass Object
                    (
                        [uid] => 26551
                        [status] => 1
                        [children] => Array
                            (
                                [25368] => stdClass Object
                                    (
                                        [uid] => 25368
                                        [status] => 1
                                    )
                            )
                    )
                [28250] => stdClass Object
                    (
                        [uid] => 28250
                        [status] => 1
                        [children] => Array
                            (
                                [28839] => stdClass Object
                                    (
                                        [uid] => 28839
                                        [status] => 1
                                        [children] => Array
                                            (
                                                [27102] => stdClass Object
                                                    (
                                                        [uid] => 27102
                                                        [status] => 1
                                                    )
                                            )
                                    )
                           )
                    )
            )
    )

)

这看起来不正确,因为这不是按所有孩子的计数排序的。排序应该根据所有后代的数量。

请检查一下。

非常感谢您的回答@trincot。

但我想我错过了一件事如果子数组的总数较大,则该数组将排在第一位。

正如在我的数组中提到的,假设我在第一个子数组中又添加了2个元素,类似于

28748 => stdClass Object
(
    [uid] => 28748
    [status] => 1
    [children] => Array
        (
            [29163] => stdClass Object
                (
                    [uid] => 29163
                    [status] => 1
                ) 
              [29173] => stdClass Object
                (
                    [uid] => 29173
                    [status] => 1
                )
               [29174] => stdClass Object
                (
                    [uid] => 29174
                    [status] => 1
                )
        )
)

第一个子数组中的子数组总数=3

第二个子数组中的子数组总数=7

但是第二子阵列中的子级的总数(也计算内部子级)更大,因此第二子数组将排在第一位。

请调查一下。

您可以使用递归函数,使用uasort:对每个级别进行排序

function sortByNumChildren(&$array) {
    foreach ($array as $key => &$obj) {
        if (isset($obj->children)) sortByNumChildren($obj->children);
    }
    uasort($array, function ($a, $b) { 
        if (!isset($a->children)) return 1;
        if (!isset($b->children)) return -1;
        return count($b->children) - count($a->children);
    });
}

调用此函数如下:

sortByNumChildren($data);

在的eval.in上查看它的运行和输出

此代码将按(直接)子级的数量进行排序。有关子体数量的排序,请参见下文。

所有子体的数量排序的代码

根据要求,这里有一段替代代码,它根据子代的数量对嵌套数组进行排序,还计算子代及其子代等

function sortByNumChildren(&$array) {
    $childCounts = array();
    foreach ($array as &$obj) {
        $childCounts[$obj->uid] = isset($obj->children) ? 
                sortByNumChildren($obj->children) : 0;
    }
    uasort($array, function ($a, $b) use ($childCounts) { 
        return $childCounts[$b->uid] - $childCounts[$a->uid];
    });
    return count($array) + array_sum($childCounts);
}

调用此函数如下:

sortByNumChildren($data);

查看它与输出一起在eval.in 上运行