汇总 List<Map<String,dynamic> 个元素

Summarize List<Map<String,dynamic> elements

我有如下销售清单:

 List<Map<String,dynamic>> sales = [
    {'paid': 2000, 'name': 'person1'},
    {'paid': 2500, 'name': 'person2'},
    {'paid': 5600, 'name': 'person1'},
    {'paid': 974.0, 'name': 'person2'},
  ];

我想汇总个人的支付金额并显示在 ListView.builder 中,如下所示:

人 1:7600 人 2 : 3474

我需要知道如何计算 Dart/Flutter 中地图内的每个人。

提前致谢。

此代码可能对您有所帮助:

   void main() {
      List<Map<String, dynamic>> sales = [
        {'paid': 2000, 'name': 'person1'},
        {'paid': 2500, 'name': 'person2'},
        {'paid': 5600, 'name': 'person1'},
        {'paid': 974.0, 'name': 'person2'},
      ];
    
      Map map = Map();
      for (var sale in sales) {
        if (map.keys.contains(sale['name'])) {
          map[sale["name"]] = map[sale["name"]] + sale['paid'];
        } else
          map[sale["name"]] = sale['paid'];
      }
      print(map.toString());
    }

输出将是:

{person1: 7600, person2: 3474.0}

我会选择一种更冗长的方法,但这样可以让您对结果保持参考。

  final List<Map<String, dynamic>> sales = [
    {'paid': 2000, 'name': 'person1'},
    {'paid': 2500, 'name': 'person2'},
    {'paid': 5600, 'name': 'person1'},
    {'paid': 974.0, 'name': 'person2'},
  ];

  final salesByName = <String, List<Map<String, dynamic>>>{};
  
  for (final entry in sales) {
    if (salesByName.keys.contains(entry["name"] as String)) {
      salesByName[entry["name"] as String]?.add(entry);
    } else {
      salesByName[entry["name"] as String] = [entry];
    }
  }

  final salesByNameSum = <String, double>{};

  for (final name in salesByName.entries) {
    print("${name.key} has ${name.value.length} entries");
    double sum = 0.0;
    for (final sale in name.value) {
      sum += sale['paid'] as double;
    }
    salesByNameSum[name.key] = sum;
  }

  for (final entry in salesByNameSum.entries) {
    print('${entry.key}: ${entry.value}');
  }

您将首先使用 name 作为键创建一个地图,并在其值中包含销售地图列表。这样您就可以轻松访问每个人的交易列表。

然后,您可以创建另一个较小的映射,仅包含 name 作为其键,并包含 sum 作为其值。

这里以 pure-dart DartPad 为例:https://dartpad.dev/?id=2f4e9b102ba931846bc8734c1180b29f

希望对您有所帮助!

还有另一种方法。按照 上使用的方法,对逻辑进行一些额外更改:

void main() {
  List<Map<String, dynamic>> sales = [
    {'paid': 2000, 'name': 'person1'},
    {'paid': 2500, 'name': 'person2'},
    {'paid': 5600, 'name': 'person1'},
    {'paid': 974.0, 'name': 'person2'},
  ];
  var result = sales.groupBy((m) => m['name']).map(
        (key, value) => MapEntry(
          key,
          value.fold<double>(0.0, (a, b) => a + b['paid']),
        ),
      );
  print(result);
}

// use this extension
extension Iterables<E> on Iterable<E> {
  Map<K, List<E>> groupBy<K>(K Function(E) keyFunction) => fold(
      <K, List<E>>{},
      (Map<K, List<E>> map, E element) =>
          map..putIfAbsent(keyFunction(element), () => <E>[]).add(element));
}

它会产生这样的东西:

{person1: 7600.0, person2: 3474.0}

你可以在 dartpad 上运行试试。