当前位置:首页 > 后端开发 > 正文内容

Flutter/Dart第04天:Dart异步编程(Future和async/await)

邻居的猫1个月前 (12-09)后端开发1700

Dart官网代码实验室:https://dart.dev/codelabs/async-await

重要阐明:本博客依据Dart官网代码实验室,但并不是简略的对官网文章进行翻译,我会依据个人研制经历,在掩盖官网文章核心内容情况下,参加自己的一些扩展问题和问题演示和总结,包含称号解说、运用场景阐明、代码样例掩盖、终究完好的场景编程等。

启蒙:过错的异步编程样例

下面是一个过错的异步编程样例,大约进程:经过模仿网络API获取订单ID,然后安排订单ID案牍,终究输出问题。

咱们希望终究输出的是正确的订单ID案牍,可成果并不契合咱们的希望:订单ID并不是T2023092900001,而是Instance of 'Future<String>'

// 1.1 创立订单音讯
String createOrderMessage() {
  var order = fetchOrderID();
  return '订单ID: $order';
}

// 1.2 获取订单ID内容
Future<String> fetchOrderID() =>
  // 假定获取订单ID是一次网络交互,处理进程需求2秒钟,因而模仿了2秒钟回来订单ID
  Future.delayed(
  const Duration(seconds: 2),
  () => 'T2023092900001',
);

void main() {
  // 1. 启蒙:过错的异步编程样例
  final message = createOrderMessage();
  print(message);

  // 成果:订单ID: Instance of 'Future<String>'
}

同步编程和异步编程阐明:

  • 同步编程:依照代码块次序履行代码块,前面代码块没有履行完结之前,后边代码被堵塞
  • 异步编程:异步操作代码块完结初始化之后,后边代码块就能够履行了(非堵塞),异步代码块履行完结(如上面样例等候2秒钟),履行完结回调代码块(即回调)。

Future异步成果阐明

异步操作的成果都是Future类的实例(https://api.dart.cn/stable/3.1.3/dart-async/Future-class.html),异步操作有2种状况:未完结完结状况。调用异步代码块(或函数),回来值都是未完结状况的成果。

  • 未完结状况:调用一个异步函数,回来一个Future<T>成果,在异步操作履行完毕或许履行犯错之前的状况。
  • 完结状况:异步操作履行完毕正常回来成果或许履行犯错,都是完结状况。正常完结的回来成果即Futrue<T>的T(如:Future<String>),假如无需回来成果,则为void,即异步函数的回来值为Future<void>。假如异步函数履行犯错,则回来成果是一个Error,能够进行捕获。

下面2个代码样例,分别为回来值为void和犯错成果:

// 2.1 异步操作无回来值
Future<void> fetchOrderID2() {
  // 模仿了2秒钟输出了订单ID
  return Future.delayed(const Duration(seconds: 2), () => print('ID2:T2023092900002'));
}

// 2.2 反常操作回来过错
Future<void> fetchOrderID3() {
  return Future.delayed(const Duration(seconds: 2), () => throw Exception('网络反常'));
}

void main() {
  // 2. Future/async/await异步成果阐明
  fetchOrderID2();
  print('2. fetchOrderID2-Future/async/await异步成果阐明...');

  // 成果:
  // 2. fetchOrderID2-Future/async/await异步成果阐明...
  // ID2:T2023092900002
  
  fetchOrderID3();
  print('2. fetchOrderID3-Future/async/await异步成果阐明...');

  // 成果:
  // 2. fetchOrderID3-Future/async/await异步成果阐明...
  // Unhandled exception:
  // Exception: 网络反常
}

async/await异步操作界说和运用

async界说一个异步操作,而await则是运用一个异步操作的成果。

在运用async和await是,有2点需求恪守的根本规矩

  1. 假如需求界说一个异步函数,则在函数体之前添加async关键字
  2. 只要在异步函数中(即函数体前有async关键字的函数),await关键字才会收效(也便是await有必要合作async运用)

界说一个异步函数办法样例(即添加async关键字):

// 1. 同步函数转异步函数:无回来成果
// 1.1 同步函数
void funcVoid() {}

// 1.2 异步回来
Future<void> funcVoid() async {}

// 2. 同步函数转异步函数:有回来成果
// 2.1 同步函数
String funcResult() {}

// 2.2 反常函数
Future<String> funcResult() async {}

接下来,咱们来重写第1张中,异步函数代码,以使成果契合咱们预期:

  1. 获取订单ID函数fetchOrderID()前,添加await关键字。
  2. 创立订单音讯的函数createOrderMessageV2(),添加async关键字变成异步函数,同回来成果由String变成Future<String>异步成果。
  3. 相同的,main()函数调用了异步函数,因而也需求添加async关键字。
// 3. async/await异步操作界说和运用
Future<String> createOrderMessageV2() async {
  var order = await fetchOrderID();
  return '订单ID: $order';
}

void main() async {
  // 3. async/await异步操作界说和运用
  final messageV2 = await createOrderMessageV2();
  print('3. async/await异步操作界说和运用');
  print('$messageV2');

  // 成果:
  // 3. async/await异步操作界说和运用
  // 订单ID: T2023092900001
}

try/catch异步操作的反常处理

在第2章节中,fetchOrderID3()异步办法会抛出反常,然后中止程序处理。异步操作的反常,咱们也能够和同步函数调用相同,经过try-catch的方法进行处理。

下面咱们把fetchOrderID3()运用的当地进行改写,捕获反常然后不中止咱们的程序:

void main() async {
  // 4. try/catch异步操作的反常处理
  try {
    await fetchOrderID3();
    print('4. try/catch异步操作的反常处理.');
  } catch (e) {
    print('4. try/catch异步操作的反常处理: $e');
  }

  // 成果:4. try/catch异步操作的反常处理: Exception: 网络反常
}

场景编程:异步编程的大合唱

运用场景假定:对当时登录的用户打个招待,一起用户退出登录。由于退出登录操作可被降级,因而退出登录需求捕获一切反常。

  1. 获取当时登录的用户名,由于是网络API操作,因而是异步操作。
  2. 退出登录时,需求获取当时缓存的用户名,规划到存储操作,因而也是异步操作。
// 5.1 拼装用户欢迎语
String makeGreeting(String userName) {
  return '欢迎你 $userName';
}

// 5.2 获取用户名,异步操作
Future<String> fetchUserName() async {
  return Future.delayed(const Duration(seconds: 2), () => 'NTopic.CN');
}

// 5.3 用户登录-打声招待
Future<String> greeting() async {
  final userName = await fetchUserName();
  return makeGreeting(userName);
}

// 5.4 用户退出-再会
Future<String> goodbye() async {
  final userName = await fetchUserName();
  return '$userName 下次再会!';
}

void main() async {
  // 5. 场景编程:异步编程的大合唱
  print('5. 场景编程:异步编程的大合唱...');
  print(await greeting());

  try {
    print(await goodbye());
  } catch (e) {
    print('5. 场景编程:异步编程的大合唱-Goodbye反常: $e');
  }

  // 成果:
  // 5. 场景编程:异步编程的大合唱...
  // 欢迎你 NTopic.CN
  // NTopic.CN 下次再会!
}

终究-完好的实例代码

本文介绍的完好的实例代码:

// 第04天:异步编程

// 1.1 创立订单音讯
String createOrderMessage() {
  var order = fetchOrderID();
  return '订单ID: $order';
}

// 1.2 获取订单ID内容
Future<String> fetchOrderID() =>
    // 假定获取订单ID是一次网络交互,处理进程需求2秒钟,因而模仿了2秒钟回来订单ID
    Future.delayed(
      const Duration(seconds: 2),
      () => 'T2023092900001',
    );

// 2.1 异步操作无回来值
Future<void> fetchOrderID2() {
  // 模仿了2秒钟输出了订单ID
  return Future.delayed(const Duration(seconds: 2), () => print('ID2:T2023092900002'));
}

// 2.2 反常操作回来过错
Future<void> fetchOrderID3() {
  return Future.delayed(const Duration(seconds: 2), () => throw Exception('网络反常'));
}

// 3. async/await异步操作界说和运用
Future<String> createOrderMessageV2() async {
  var order = await fetchOrderID();
  return '订单ID: $order';
}

// 5.1 拼装用户欢迎语
String makeGreeting(String userName) {
  return '欢迎你 $userName';
}

// 5.2 获取用户名,异步操作
Future<String> fetchUserName() async {
  return Future.delayed(const Duration(seconds: 2), () => 'NTopic.CN');
}

// 5.3 用户登录-打声招待
Future<String> greeting() async {
  final userName = await fetchUserName();
  return makeGreeting(userName);
}

// 5.4 用户退出-再会
Future<String> goodbye() async {
  final userName = await fetchUserName();
  return '$userName 下次再会!';
}

void main() async {
  // 1. 启蒙:过错的异步编程样例
  final message = createOrderMessage();
  print(message);

  // 2. Future/async/await异步成果阐明
  fetchOrderID2();
  print('2. fetchOrderID2-Future/async/await异步成果阐明...');

  // fetchOrderID3();
  print('2. fetchOrderID3-Future/async/await异步成果阐明...');

  // 3. async/await异步操作界说和运用
  final messageV2 = await createOrderMessageV2();
  print('3. async/await异步操作界说和运用');
  print('$messageV2');

  // 4. try/catch异步操作的反常处理
  try {
    await fetchOrderID3();
    print('4. try/catch异步操作的反常处理.');
  } catch (e) {
    print('4. try/catch异步操作的反常处理: $e');
  }

  // 5. 场景编程:异步编程的大合唱
  print('5. 场景编程:异步编程的大合唱...');
  print(await greeting());

  try {
    print(await goodbye());
  } catch (e) {
    print('5. 场景编程:异步编程的大合唱-Goodbye反常: $e');
  }
}

我的本博客原地址:https://ntopic.cn/p/2023092901


扫描二维码推送至手机访问。

版权声明:本文由51Blog发布,如需转载请注明出处。

本文链接:https://www.51blog.vip/?id=279

分享给朋友:

“Flutter/Dart第04天:Dart异步编程(Future和async/await)” 的相关文章

manim边做边学--多面体

manim边做边学--多面体

在Manim中,关于多面体,有一系列封装好的类能够直接运用。 运用它们,能够便利快速的构建正多面体: Polyhedron:经过极点和面的参数构建恣意多面体 Tetrahedron:四面体 Octahedron:八面体 Dodecahedron:十二面体 Icosahedron:二十面体 这些类使得...

愤怒的小鸟go

《愤怒的小鸟GO》是由Rovio公司开发的一款以愤怒的小鸟为主题的卡丁赛车游戏。与传统的愤怒的小鸟系列游戏不同,这款游戏不再是弹射小鸟攻击肥猪,而是将小鸟和肥猪作为赛车手进行竞速比赛。 游戏介绍《愤怒的小鸟GO》于2013年12月11日上线,是一款全新的竞速游戏。玩家可以选择小鸟或肥猪作为赛车手,驾...

delphi为什么没人用了,Delphi为何逐渐淡出开发者视野?

Delphi 是一种编程语言和集成开发环境(IDE),由 Borland(现在的 Embarcadero Technologies)开发,主要面向 Windows 平台。它在 1990 年代和 2000 年代初期非常流行,尤其是在桌面应用开发领域。随着时间的推移,Delphi 的使用逐渐减少,原因可...

计算机二级c语言答案,计算机二级C语言考试答案解析

计算机二级c语言答案,计算机二级C语言考试答案解析

你可以通过以下资源获取计算机二级C语言的真题及答案:1. 历年计算机二级C语言真题及答案: 这里提供了历年计算机二级C语言的真题及答案,可以在线评测。2. C语言二级题库带答案 解析: 该文档包含程序设计题的题目、程序(含空)以及答案,适合进行练习。3. 2023年全国计...

rust木门怎么拆,Rust游戏中的木门拆除方法详解

rust木门怎么拆,Rust游戏中的木门拆除方法详解

拆装木门是一项需要谨慎操作的任务,尤其是对于初学者来说。下面是一些基本的步骤,可以帮助你安全地拆下Rust木门:1. 准备工具:在开始之前,确保你拥有必要的工具,如螺丝刀、锤子、凿子、钳子等。2. 断电:如果门附近有电源插座或开关,请先关闭电源,以避免触电风险。3. 拆卸门把手和锁:首先,卸下门把手...

php架构, 系统架构概述

php架构, 系统架构概述

2. 三层架构:三层架构是将应用程序分为表现层、业务逻辑层和数据访问层。表现层负责与用户交互,业务逻辑层处理应用程序的核心功能,数据访问层负责与数据库交互。3. 依赖注入(DI):依赖注入是一种设计模式,它允许在运行时动态地将依赖项注入到对象中。这有助于减少代码耦合,提高代码的可测试性和可维护性。4...