Dart
中有类似于Javascript
的async/await
语法,用以支持异步场景。在Dart
里,很多库方法会返回Future
或者Stream
对象,这些方法是异步的。对于这些方法,它们会在调用完后就返回了,这种情况下,如何获得调用结果呢?方法有两种:
- 使用
async
/await
- 使用
Future API
同样地,从Stream
中获取数据的方式也有两种:
- 使用
async
和异步for
(await for
) - 使用
Stream API
我们都知道,使用async/await
的好处,便是可以使得异步代码写起来像同步代码,如:await lookUpVersion()
一、async关键字
async
和await
是配套使用的,即使用await
时,其方法必须带有async
关键字,如:
checkVersion() async {
var version = await lookUpVersion();
if (version == expectedVersion) {
// ...
} else {
// ...
}
}
因此,使用async
关键字可以声明一个异步方法,即:
checkVersion() async {
// ...
}
lookUpVersion() async => /* ... */
async
方法返回值类型为Future
,如:
Future<String> lookUpVersion() async => '1.0.0'
二、await
await
的语法如下:
await expression
一个异步方法内部可以多次地使用await
表达式,如:
buyItem(int id) async {
var remainedCount = await getItemRemainedNumber(id);
var stockUpdatedRes = await updateStock(id);
return stockUpdatedRes;
}
对于await expression
而言,expression
应该是一个Future
对象,如果expression
不是一个Future
对象,则Dart
会自动地将它转为Future
对象
三、异常处理
处理await
异常,可以使用try...catch...finally
语句块,如:
try {
var server = await HttpServer.bind(InternectAddress.LOOPBACK_IP_V4, 4044);
} catch (e) {
// ...
}
四、在循环中使用异步
异步for
循环的语法形式如下:
await for (variable declaration in expression) {
// ...
}
其中,expression
的类型必须是Stream
类型,并且执行流程为:
- 等待直到
stream
返回一个数据 - 使用
stream
返回的参数执行for
循环代码 - 重复执行步骤1和步骤2,直到stream数据返回完毕
- 如果遇到
break
或者return
语句,可以提前停止接收stream
的数据
注意: 异步for也需要在
async
方法里执行,如果要在main()
方法里执行,则main()
方法要标记为async
例子:
main() async {
// ...
await for (var request in requestServer) {
handleRequest(request);
}
// ...
}