Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: function array_group_by #7438

Merged
merged 12 commits into from
May 14, 2023
65 changes: 65 additions & 0 deletions system/Helpers/array_helper.php
Original file line number Diff line number Diff line change
Expand Up @@ -218,3 +218,68 @@ function array_flatten_with_dots(iterable $array, string $id = ''): array
return $flattened;
}
}

if (! function_exists('array_group_by')) {
/**
* Groups all rows by their index values. Result's depth equals number of indexes
*
* @param array $array Data array (i.e. from query result)
* @param array $indexes Indexes to group by. Dot syntax used. Returns $array if empty
* @param bool $includeEmpty If true, null and '' are also added as valid keys to group
*
* @return array Result array where rows are grouped together by indexes values.
*/
function array_group_by(array $array, array $indexes, bool $includeEmpty = false): array
{
if ($indexes === []) {
return $array;
}

$result = [];

foreach ($array as $row) {
$result = _array_attach_indexed_value($result, $row, $indexes, $includeEmpty);
}

return $result;
}
}

if (! function_exists('_array_attach_indexed_value')) {
/**
* Used by `array_group_by` to recursively attach $row to the $indexes path of values found by
* `dot_array_search`
*
* @internal This should not be used on its own
*/
function _array_attach_indexed_value(array $result, array $row, array $indexes, bool $includeEmpty): array
{
if (($index = array_shift($indexes)) === null) {
$result[] = $row;

return $result;
}

$value = dot_array_search($index, $row);

if (! is_scalar($value)) {
$value = '';
}

if (is_bool($value)) {
$value = (int) $value;
}

if (! $includeEmpty && $value === '') {
return $result;
}

if (! array_key_exists($value, $result)) {
$result[$value] = [];
}

$result[$value] = _array_attach_indexed_value($result[$value], $row, $indexes, $includeEmpty);

return $result;
}
}
Loading