📜  Dart – 并发(1)

📅  最后修改于: 2023-12-03 15:14:36.314000             🧑  作者: Mango

Dart – 并发

在 Dart 语言中,我们可以通过 async 和 await 关键字来实现并发操作。Dart 中的并发操作又叫做异步操作,即在执行任务的过程中,可以让执行其他的任务而不阻塞主线程。

Future

在 Dart 中,我们可以使用 Future 类来实现异步操作。Future 表示一个延迟的操作,它可能在未来完成并返回结果。

基本使用
void main() {
  print('main start');
  Future<String>.delayed(Duration(seconds: 1), () {
    return 'hello';
  }).then((value) {
    print(value); // 输出 hello
  });
  print('main end');
}

上面的代码中,我们使用了 Future.delayed 方法来创建一个延时操作。在1秒后执行,返回字符串 'hello'。通过 then 方法,我们监控了这个异步操作的完成,并输出结果。

输出结果为:

main start
main end
hello

在 main 函数执行到 Future.delayed 方法时,它是异步执行的,所以不会阻塞主线程。因此,main end 会在 hello 之前输出。

错误处理

在异步操作中,我们也需要考虑到可能的错误情况。可以通过 catchError 或者默认值来处理 Future 返回的错误。

void main() {
  print('main start');
  Future<String>.delayed(Duration(seconds: 1), () {
    return 'hello';
  }).then((value) {
    // 使用未定义的变量导致的异常
    var a;
    var b = a.length;
    print(value); // 此处不会执行,因为上面 a.length 抛出了异常
  }).catchError((e) {
    print('catch error: $e'); // 输出 catch error: NoSuchMethodError: The getter 'length' was called on null.
  });
  print('main end');
}

output:

main start
main end
catch error: NoSuchMethodError: The getter 'length' was called on null.
并发处理多个 Future

在 Dart 中,我们可以使用 Future.wait 来创建一个新的 Future。我们可以用它来在所有操作完成后返回一个 Future,它可以用来等待异步任务的完成并依次对它们进行处理。

void main() {
  print('main start');
  Future<String> op1 = Future<String>.delayed(Duration(seconds: 1), () {
    return 'hello';
  });
  Future<String> op2 = Future<String>.delayed(Duration(seconds: 2), () {
    return 'world';
  });
  Future.wait<String>([op1, op2]).then((values) {
    print(values); // 输出 [hello, world]
  });
  print('main end');
}

output:

main start
main end
[hello, world]
async 和 await

在 Dart 中,我们可以使用 async 和 await 关键字来实现异步处理。async 和 await 同样使用了 Future,只不过是通过它们来简化了异步代码中的写法。

基本使用
void main() {
  testAsync();
  print('main end');
}

testAsync() async {
  print('testAsync start');
  String value = await Future<String>.delayed(Duration(seconds: 1), () {
    return 'hello';
  });
  print(value);
  print('testAsync end');
}

output:

main end
testAsync start
hello
testAsync end

在上面的代码中,我们声明了一个异步函数 testAsync,它通过 await 关键字等待一个异步操作 Future 完成,并获取返回值 'hello'。在函数执行期间,main 函数会继续执行而不会阻塞。

错误处理

我们也可以在异步函数中使用 try-catch 来处理可能出现的错误。

void main() {
  testAsync();
  print('main end');
}

testAsync() async {
  print('testAsync start');
  try {
    String value = await Future<String>.delayed(Duration(seconds: 1), () {
      // 一个会抛出异常的异步操作
      throw 'error';
    });
    print(value);
  } catch (e) {
    print('catch error: $e'); // 输出 catch error: error
  }
  print('testAsync end');
}

output:

main end
testAsync start
catch error: error
testAsync end
并发处理多个 Future

我们还可以使用 async 和 await 关键字来实现多个异步任务的并行处理。

void main() {
  testAsync();
  print('main end');
}

testAsync() async {
  print('testAsync start');
  Future<String> op1 = Future<String>.delayed(Duration(seconds: 1), () {
    return 'hello';
  });
  Future<String> op2 = Future<String>.delayed(Duration(seconds: 2), () {
    return 'world';
  });
  var values = await Future.wait<String>([op1, op2]);
  print(values); // 输出 [hello, world]
  print('testAsync end');
}

output:

main end
testAsync start
[hello, world]
testAsync end
Conclusion

通过本文,您应该掌握了在 Dart 中实现并发操作的基本方法。异步操作可以帮助我们更加高效地编写代码,并在程序运行期间处理大量数据。您可以在实际项目中灵活运用。