天天看點

php 使用 array_reduce 實作多元數組分組(groupby)聚合

在處理關聯數組時,經常需要對多元數組按指定字段分組聚合,下面封裝了一個數組分組聚合方法:

/**
 * 對數組進行分組聚合
 * @param $array
 * @param $keys
 * @return $result
 */
function array_group_by($array, $keys)
{
	if(!is_array($keys) || count($keys) == 1)
    {
        $key = is_array($keys) ? array_shift($keys) : $keys;

        return array_reduce($array, function($tmp_result, $item) use ($key)
        {
            $tmp_result[$item[$key]][] = $item;

            return $tmp_result;
        });
    }
    else
    {
        $keys = array_values($keys);

        $result = array_group_by($array, array_shift($keys));

        foreach ($result as $k=>$value)
        {
            $result[$k] = array_group_by($value, $keys);
        }

        return $result;
    }
}

           

測試:

$arr = [
     [
       "first" => "aa",
       "second" => "ccc",
       "third" => "sdfgg",
     ],
     [
       "first" => "aa",
       "second" => "ccc",
       "third" => "dddsa",
     ],
     [
       "first" => "aa",
       "second" => "sdfsdfd",
       "third" => "sdfgg",
     ],
     [
       "first" => "bb",
       "second" => "ccc",
       "third" => "sdfgg",
     ],
     [
       "first" => "bb",
       "second" => "sdfsdfd",
       "third" => "sdfgg",
     ],
   ];
	
	print_r(array_group_by($arr, ['first']));
	/*
	[
     "aa" => [
       [
         "first" => "aa",
         "second" => "ccc",
         "third" => "sdfgg",
       ],
       [
         "first" => "aa",
         "second" => "ccc",
         "third" => "dddsa",
       ],
       [
         "first" => "aa",
         "second" => "sdfsdfd",
         "third" => "sdfgg",
       ],
     ],
     "bb" => [
       [
         "first" => "bb",
         "second" => "ccc",
         "third" => "sdfgg",
       ],
       [
         "first" => "bb",
         "second" => "sdfsdfd",
         "third" => "sdfgg",
       ],
     ],
   ]
	*/
	print_r(array_group_by($arr, ['first','second']));
	/*
	[
     "aa" => [
       "ccc" => [
         [
           "first" => "aa",
           "second" => "ccc",
           "third" => "sdfgg",
         ],
         [
           "first" => "aa",
           "second" => "ccc",
           "third" => "dddsa",
         ],
       ],
       "sdfsdfd" => [
         [
           "first" => "aa",
           "second" => "sdfsdfd",
           "third" => "sdfgg",
         ],
       ],
     ],
     "bb" => [
       "ccc" => [
         [
           "first" => "bb",
           "second" => "ccc",
           "third" => "sdfgg",
         ],
       ],
       "sdfsdfd" => [
         [
           "first" => "bb",
           "second" => "sdfsdfd",
           "third" => "sdfgg",
         ],
       ],
     ],
   ]
	*/