既然 Dart 中有模式匹配,最好用它来迭代映射吗?

问题描述 投票:0回答:1

传统上,要迭代

Map
的键和值,您可以这样写:

  map.forEach((key, value) {

  });

但是随着 Dart 3.0 中引入patterns,你实际上可以将其写为

  for (var MapEntry(:key, :value) in map.entries) {

  }

事实上,这样的构造在For 和 for-in 循环部分的模式文档中给出了示例。

我想这是否是一种更好的代码风格是主观的,但在性能/内存方面是否有一种方法比另一种更好?

dart pattern-matching
1个回答
0
投票

可以通过基准来评估性能:

import 'package:benchmark_runner/benchmark_runner.dart';

void main(List<String> args) {
  final mapSize = 100000;
  final list = List<int>.generate(mapSize, (index) => index);
  final map = {for (var element in list) element: element.toString()};
  final result = <int, String>{};

  benchmark('Iterating using forEach: map size $mapSize', () {
    map.forEach((key, value) {
      result[key] = '$value-new';
    });
  });
  result.clear();
  benchmark('Iterating over map keys: map size $mapSize', () {
    for (final key in map.keys) {
      result[key] = '${map[key]!}-new';
    }
  });
  result.clear();
  benchmark('Pattern for loop: map size $mapSize', () {
    for (final MapEntry(:key, :value) in map.entries) {
      result[key] = '$value-new';
    }
  });
}

地图尺寸 100 的基准分数:

[244ms:881us] Iterating using forEach: map size 100
    mean: 7.24 ± 1.030 us, median: 7.032 ± 0.66 us
    ▆▉▂▂____________ sample size: 40 (averaged over 131 runs)
  
[242ms:617us] Iterating over map keys: map size 100
    mean: 7.50 ± 0.42 us, median: 7.51 ± 0.49 us
    ▆▄▉▁___ sample size: 41 (averaged over 124 runs)
  
[236ms:322us] Pattern for loop: map size 100
    mean: 9.12 ± 0.48 us, median: 9.11 ± 0.69 us
    ▇▉▄▁_ sample size: 30 (averaged over 115 runs)

地图大小 100000 的基准分数:

[811ms:165us] Iterating using forEach: map size 100000
    mean: 10.47 ± 1.97 ms, median: 9.60 ± 1.66 ms
    ▉▁▃________ sample size: 49
  
[890ms:338us] Iterating over map keys: map size 100000
    mean: 12.18 ± 2.013 ms, median: 11.20 ± 2.31 ms
    ▉▁▅______ sample size: 48
  
[01s:004ms] Pattern for loop: map size 100000
    mean: 14.47 ± 2.63 ms, median: 13.97 ± 2.51 ms
    ▉▃▇_________ sample size: 47

地图大小 1000000 的基准分数:

[04s:144ms] Iterating using forEach: map size 1000000
    mean: 217.80 ± 12.30 ms, median: 214.88 ± 18.029 ms
    ▉▇▂▄ sample size: 10
  
[06s:004ms] Iterating over map keys: map size 1000000
    mean: 353.59 ± 28.75 ms, median: 358.84 ± 57.83 ms
    ▇▄▂▉ sample size: 10
  
[06s:947ms] Pattern for loop: map size 1000000
    mean: 413.17 ± 10.85 ms, median: 413.095 ± 16.46 ms
    ▄▉▄▄ sample size: 10

结论:使用

forEach
迭代映射键时,基准分数显示出稍好的性能。然而,对于中等大小的地图,性能增益太小,无法推荐一种风格而不是另一种风格。

© www.soinside.com 2019 - 2024. All rights reserved.