groupBy<T, String> method

Map<String, List<T>> groupBy<T, String>(
  1. String mapper(
    1. T e
    ), {
  2. Iterable order = const [],
  3. Iterable pinned = const [],
})

Groups the elements of the current Iterable by a key derived from each element.

The function takes a key parameter, which represents a function that derives the key from each element in the Iterable. It creates a new Map with the derived keys as the keys and lists of elements as the values.

If an order is provided, it orders the resulting Map based on the specified keys.

Returns a new Map with the elements grouped by the derived keys.

Example:

List<String> names = ['Alice', 'Bob', 'Charlie', 'Alex', 'Brian', 'Chris'];
final Map<String, List> scopes = widget.tasks.groupBy<Task, String>(
        (entity) => entity.priority,
        order: ['df', 'sc', 'de', 'dd'],
      );
print(grouped);
// Output: {5: [Alice, Brian], 3: [Bob], 7: [Charlie], 4: [Alex, Chris]}

Implementation

Map<String, List<T>> groupBy<T, String>(String Function(T e) mapper,
    {Iterable order = const [], Iterable pinned = const []}) {
  final Map<String, List<T>> data = {};
  final Map<String, List<T>> ordered = {};

  for (final dynamic e in this) {
    final List<T> entities = data.putIfAbsent(mapper(e as T), () => []);
    entities.add(e);
  }

  if (order.isNotEmpty) {
    for (String e in order) {
      if (data[e] != null) {
        ordered[e] = data[e]!;
      }
    }
  } else {
    final List<String> dataKeys = data.keys.toList();
    final List<String> sortedKeys = dataKeys.sorted();

    for (String key in sortedKeys) {
      ordered[key] = data[key] ?? [];
    }
  }

  if (pinned.isNotEmpty) {
    final Map<String, List<T>> pinnedData = {};
    for (String p in pinned) {
      if (ordered.containsKey(p)) {
        pinnedData[p] = ordered.remove(p)!;
      }
    }

    pinnedData.addAll(ordered);
    return pinnedData;
  }

  return ordered;
}