Future.wait 在 Dart 中真的是异步的吗?

Is Future.wait trully asynchonous in Dart?

我需要等待许多 Future 完成他们的计算,一堆 HTTP 请求,我不想 await 所有这些都按顺序进行,因为这将导致每个 Future 按顺序评估,一个接一个,有点同步,这很浪费,因为一些 Future 可能比其他的更快完成。

我在文档中找不到 Future.wait 是真正的异步,同时触发所有 Future,或者是否与一个接一个地调用它们一样,等待上一个完成调用下一个。

简而言之:我正在寻找在 Dart 中获取许多 HTTP 请求结果的最佳性能方法。

如果检查 Future.wait 方法的实现:

https://github.com/dart-lang/sdk/blob/a75ffc89566a1353fb1a0f0c30eb805cc2e8d34c/sdk/lib/async/future.dart#L354-L443

您实际上可以看到它遍历输入列表中的每个 Future 和 运行s then 方法,当 Future 完成:

      for (var future in futures) {
        int pos = remaining;
        future.then((T value) {
        ...

因此您可以说所有 Future 个实例同时 "started" 因为每个完成的 Future 最终都会检查是否有更多的 futures 等待。

但是,请注意 Dart 是单线程的,在后台有一个作业队列,所以除非一些工作在 Isolate 个实例中完成,否则每个作业将在 运行ning 结束串行。有关此的更多详细信息,请参见此处:

https://medium.com/dartlang/dart-asynchronous-programming-isolates-and-event-loops-bffc3e296a6a

但是,是的,如果你有一堆 if Future 可以按任何顺序处理,那么使用 Future.wait 方法是有意义的。

Future.wait 确实以异步方式等待多个期货,因为每个期货都是独立启动的。相比之下,Future.forEach 将循环遍历期货列表并按顺序等待它们。

例如,如果您有以下期货清单:

var futures = [
  Future.delayed(Duration(seconds, 3)).then((_) => print('1')),
  Future.delayed(Duration(seconds, 2)).then((_) => print('2')),
  Future.delayed(Duration(seconds, 1)).then((_) => print('3')),
];

在此列表上调用 Future.wait 将产生以下输出:

3 (after 1 second)
2 (after 2 seconds)
1 (after 3 seconds)

而在列表中调用 Future.forEach 会导致:

1 (after 3 seconds)
2 (after 5 seconds)
3 (after 6 seconds)

这是因为 wait 同时触发它们,然后在它们全部解决时处理它们,而 forEach 按顺序分别触发它们并等待每个解决,然后再进入下一个。

(这里是通常的免责声明,即异步编程与并行编程不同,Dart 本质上是一种单线程语言,因此仅靠 futures 无法实现真正​​的并行性。)