Dart之Future

Future

Dart类库有非常多的返回Future或者Stream对象的函数。 这些函数被称为异步函数:它们只会在设置好一些耗时操作之后返回,比如像 IO操作。而不是等到这个操作完成。
async和await关键词支持了异步编程,允许您写出和同步代码很像的异步代码。

1. Future.then

使用 Future.delayed 模拟一个耗时操作,2秒后返回字符串“Hello Dart”,然后在then中接收到异步返回值,并打印出来:

Future.delayed(new Duration(seconds: 2), () {
      return "Hello Dart";
    }).then((value) => print(value));

输出结果
2秒后返回

2. Future.catchError

如果异步任务发生错误,我们可以在catchError中捕获错误:

   Future.delayed(new Duration(seconds: 2), () {
//      return "Hello Dart";
      throw AssertionError('Error');
    }).then((value) {
      print('success');
    }).catchError((e) {
      print(e);
    });

输出结果:
在这里插入图片描述
上面的代码中,在返回时没有返回数据,而是直接抛出一个异常,then方法没有回调,而是走的catchError。这是一种异常捕获方式,另外一种是直接用then方法的可选参数onError来捕获:

 Future.delayed(new Duration(seconds: 2), () {
//      return "Hello Dart";
      throw AssertionError('Error');
    }).then((value) {
      print('success');
    },onError: (e){
      print(e);
    });

输出结果与上面一致。

3. Future.whenComplete

当请求结束后处理一些操作(无论请求成功还是失败,比如取消loading等操作),那么使用whenComplete回调:

  Future.delayed(new Duration(seconds: 2), () {
//      return "Hello Dart";
      throw AssertionError('Error');
    }).then((value) {
      //success
      print('success');
    }).catchError((e) {
      //error
      print(e);
    }).whenComplete(() {
      print('whenComplete');
    });

输出结果:
在这里插入图片描述

4. Future.wait

使用Future.wait 是一个界面同时发起多个请求时,需要这几个请求都获取数据成功再处理页面UI展示时使用。比如两个网络请求,这俩请求都返回成功后才执行 then,只要有一个返回失败,就会走error回调。

Future.wait([
      //2s后返回
      Future.delayed(new Duration(seconds: 2), () {
        return 'Hello';
      }),

      //4s后返回
      Future.delayed(new Duration(seconds: 4), () {
        return 'Dart';
      })
    ]).then((value) {
      //success
      print(value[0] + value[1]);
    }).catchError((e) {
      //error
      print(e);
    });

4s后输出结果:
在这里插入图片描述

如果第一个请求抛出异常,那么4s后就会走失败的回调:

  Future.wait([
      //2s后返回
      Future.delayed(new Duration(seconds: 2), () {
//        return 'Hello';
        throw AssertionError('first future error');
      }),

      //4s后返回
      Future.delayed(new Duration(seconds: 4), () {
        return 'Dart';
      })
    ]).then((value) {
      //success
      print(value[0] + value[1]);
    }).catchError((e) {
      //error
      print(e);
    });

输出结果:
在这里插入图片描述

5. await和async

方法返回一个Future表示该方法中含有耗时操作,当执行到耗时操作的时候,该方法就直接返回一个Future,从而使得调用该方法的外层方法不去理会该耗时操作继续执行后面的代码避免阻塞;值得注意的是如果一个方法声明返回的类型是Future对象,但其内部根本没有耗时操作,那么该方法根本就没有必要声明返回一个Future。而对于一个含有耗时操作的方法(返回Future)来说,虽然在其调用的地方该方法返回了一个Future,但是在该方法自己内部是阻塞了的(阻塞在await处)。await关键字的作用就是等待耗时操作,比如一个http.get方法是一个耗时操作,其返回Future,如果调用的时候没有用await修饰,那么代码执行到http.get处时直接跳过(因为http.get返回的是Future)从而避免阻塞,但是如果调用的时候声明了await,那么方法会阻塞到http.get处,且调用http.get的方法也会返回Future(因为其内部含有耗时操作).而出现await的方法必须用async修饰。

1. 没有耗时操作的Future方法

void main() async{
  print(DateTime.now().millisecondsSinceEpoch);
  await b();
  print(DateTime.now().millisecondsSinceEpoch);
}

Future b() async{
  Future.delayed(Duration(seconds: 5));
  print('bbb');
  return null;
}

输出结果:
在这里插入图片描述

2. 含有耗时操作的Future方法

void main() async{
  print(DateTime.now().millisecondsSinceEpoch);
  await b();
  print(DateTime.now().millisecondsSinceEpoch);
}

Future b() async{
  await Future.delayed(Duration(seconds: 5));
  print('bbb');
  return null;
}

输出结果:
在这里插入图片描述
等待b方法执行完5s后再打印。

3. 含有耗时操作不等待

void main() async{
  print(DateTime.now().millisecondsSinceEpoch);
  b();
  print(DateTime.now().millisecondsSinceEpoch);
}

Future b() async{
  await Future.delayed(Duration(seconds: 5));
  print('bbb');
  return null;
}

输出结果:
在这里插入图片描述
方法b中有耗时操作,但是main方法中没有等待b执行完成。

你可能感兴趣的:(Android,Flutter,android,flutter,dart)