Flutter学习—Dart的异步(async await)和Future对象的使用

因为Dart是单线程的语言,所以如果线程中顺序执行的时候如果遇到一些耗时阻塞的操作,比如数据请求,延时操作等,就会产生卡顿,所以用异步来解决。
异步代码主要是用async await实现,熟悉js的同学应该非常熟悉,这里的使用方法也和js很像。这里举个简单的例子说明(代码比较随意只是为了解释用)

这里_request是一个简单的get请求,返回response数据;

_request() async {
    var request = await new HttpClient()
        .getUrl(Uri.parse('http://api.apiopen.top/recommendPoetry'));
    var response = await request.close();
    String responseBody = await response.transform(utf8.decoder).join();
    return responseBody;
}

随便在个按钮的onPressed里面添加个方法,来调用_request获取请求结果。

onPressed: () {
  String responseBody = _request();
  print(responseBody);
}

此时调用会报错
flutter: type 'Future' is not a subtype of type 'String'
改动一下代码,将async添加到方法声明处,await添加到调用的方法之前,这样就不会报错。

onPressed: () async {
  String responseBody = await _request();
  print(responseBody);
}

下面具体分析一下:
(1)第一个例子中,_request()方法是网络请求,是耗时操作,所以是用async标记的,表示函数内部包含有需要延迟执行的代码,而await标记的方法就是需要延迟执行的,会将其放入延迟的队列中。而用await标记的方法返回的都是一个Future对象,所以第一种写法会报错,因为返回的是Future类型而不是String。
(2)第二个例子,添加async,await标识,这样会先执行_request()方法,等待其执行完成后return结果再继续执行。

以上就是async await的使用。

Future
那么上面提到了Future对象,它也是Dart语言里内置的,文档的解释是用来表示一个潜在的value或error,并且Future的接收者可以注册一个一旦可用就处理value和error的回调。

下面写个例子,还是调用上面的_request()请求:
Future中T是Object可以指定返回类型。

  Future<String> testFutureStr() async {
    String responseBody = await _request();
    return "测试例子"+responseBody;
  }

调用的时候除了使用async await也可以使用类似es6的链式调用

onPressed: () async {
  String responseBody = await _request();
  print(responseBody);
}

onPressed: () {
  testFutureStr().then((responseBody){
         print(responseBody);
   });
},

还可以对异常进行捕获,改动一下第一个方法,手动抛出一个错误

 Future<String> testFutureStr() async {
    String responseBody = await _request();
    throw ('这是一个错误测试');
  }

下面对异常捕获,也是种写法,async await用catch捕获,链式调用catchError方法

onPressed: () async {
      try{
         await testFutureStr();
       }catch(e){
        //捕获异常
         print(e);
       }
    }

//链式调用
onPressed: () async {
  testFutureStr().then((str){print(str);}).catchError((error) {
    				//捕获异常
            print(error);
          });
},

Future还有别的使用方法,在关于Dart线程事件会再说Future的microtask方法。

猜你喜欢

转载自blog.csdn.net/github_33420275/article/details/88063322