我有一个数据的集合。
$array = [
[
'id' => 1,
'name' => 'some1',
'type' => 'type1',
'color' => 'color1',
'quantity' => 1
],
[
'id' => 2,
'name' => 'some1',
'type' => 'type1',
'color' => 'color1',
'quantity' => 1
],
[
'id' => 3,
'name' => 'some1',
'type' => 'type1',
'color' => 'color2',
'quantity' => 1
],
[
'id' => 4,
'name' => 'some2',
'type' => 'color1',
'color' => 'type1',
'quantity' => 1
],
......
];
具有不同的名称、类型和颜色。
我想按名称、类型和颜色对数据进行分组,结果是带有相同组数据的摘要的数组数据。
首先,我使用这种方式:
function groupedData($array)
{
$collection = [];
collect($array)->groupBy('name')->map(
function ($item) use (&$collection) {
return $item->groupBy('type')->map(
function ($item) use (&$collection) {
return $item->groupBy('color')->map(
function ($item) use (&$collection) {
$quantity = $item->sum('quantity');
$collection[] = collect($item[0])->merge(compact('quantity'));
}
);
}
);
}
);
return $collection;
}
我希望输出应该是这样的:
$grouped = [
[
'id' => 1,
'name' => 'some1',
'type' => 'type1',
'color' => 'color1',
'quantity' => 2
],
[
'id' => 2,
'name' => 'some1',
'type' => 'type1',
'color' => 'color2',
'quantity' => 1
],
[
'id' => 3,
'name' => 'some2',
'type' => 'type1',
'color' => 'color1',
'quantity' => 2
],
[
'id' => 4,
'name' => 'some2',
'type' => 'type2',
'color' => 'color1',
'quantity' => 2
],
];
其中,数量表示组项目的数量。
但是,我的问题是当所需更改时。以防万一:当用户想要添加其他类别进行分组时,例如:用户可能希望按名称,类型,颜色和大小进行分组。
问:如何做一个函数,让它更加简单灵活,所以在需要改变的时候不需要改变代码吗?
谢谢你的回答。
你要找的东西是排序,而不是分组。
这里有一个简单的方法:
function sort($array, $keys) {
return collect($array)->sortBy(function ($item) use ($keys) {
return array_reduce($keys, function ($carry, $key) use ($item) {
return $carry + $item[$key];
}, '');
})->all();
}
这里有一个简短的解释:
- 我们使用的是集合的
sortBy
方法,该方法让我们使用一个回调函数,该函数将返回一个字符串来确定排序顺序。 - 我们使用键上的
array_reduce
来构建要排序的键中所有值的单个字符串。 - Laravel 的集合对象将使用该生成的字符串对集合进行排序。
- 最后,我们调用
all
方法从集合中获取基础数组。如果要实际返回集合,可以删除最后一个all
调用。