微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

有没有办法使用 Dart/Flutter 访问 ForEach 中的索引/键

如何解决有没有办法使用 Dart/Flutter 访问 ForEach 中的索引/键

我正在尝试运行以下 foreach 循环,以便删除特定条目。

textMap.results.forEach((element) {
   textMap.results.removeAt(**element.KEY**);
   print(element.KEY)
}

是否可以引用 foreach 循环的索引/键?? 我已经使用基本迭代器对此进行了测试,但是如果列表包含多个需要删除的条目,那么一旦删除了初始项目,索引就会变得不同步。这就是为什么我要寻找索引/键

解决方法

首先,avoid using Iterable.forEach except for trivial cases。如果您需要元素索引,只需使用普通的循环结构(例如 forwhile)。另见https://stackoverflow.com/a/65420010/

在您的示例代码中,您无条件地删除了每个项目,因此您可以在最后调用 List.clear(),这样会更简单、更高效。那应该是 O(1)。

如果您不想删除所有项目,而是需要有条件删除多个项目,您可以通过几种方法来实现。

  • 如果可能,请使用 List.removeWhere。我希望这对于列表的长度是 O(n)。

  • 从最后到第一项处理项目,以便从列表中删除元素不会影响迭代:

    for (var i = textMap.results.length - 1; i >= 0; i -= 1) {
      print(textMap.results[i]); // Do something with the element.
      if (shouldRemove(textMap.results[i])) {
        textMap.results.removeAt(i);
      }
    }
    
  • 如果一定要按顺序处理元素,可以先收集一个要删除的索引列表,然后再分别删除:

    var indicesToRemove = <int>[];
    for (var i = 0; i < textMap.results.length; i += 1) {
      print(textMap.results[i]); // Do something with the element.
      if (shouldRemove(textMap.results[i])) {
        indicesToRemove.add(i);
      }
    }
    // Remove in reverse order so that removing items does not affect
    // unprocessed indices.
    for (var index in indicesToRemove.reversed) {
      textMap.results.removeAt(index);
    }
    
  • 或者使用 while 循环有条件地增加列表索引:

    var i = 0;
    while (i < textMap.results.length) {
      print(textMap.results[i]); // Do something with the element.
      if (shouldRemove(textMap.results[i])) {
        textMap.results.removeAt(i);
        // Iterate again at the same index.
        continue;
      }
      i += 1;
    }
    

最后三种方法是 O(m*n),其中 n 是列表的长度,m 是要删除的项目数。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。