首页 > 其他分享 >HarmonyOS:异步并发 (Promise和async/await)

HarmonyOS:异步并发 (Promise和async/await)

时间:2024-12-01 23:32:08浏览次数:9  
标签:异步 并发 await HarmonyOS Promise result async

一、并发概述

并发是指在同一时间内,存在多个任务同时执行的情况。对于多核设备,这些任务可能同时在不同CPU上并行执行。对于单核设备,多个并发任务不会在同一时刻并行执行,但是CPU会在某个任务休眠或进行I/O操作等状态下切换任务,调度执行其他任务,提升CPU的资源利用率。


为了提升应用的响应速度与帧率,避免耗时任务对UI主线程的影响,ArkTS提供了异步并发和多线程并发两种处理策略。

  • 异步并发是指异步代码在执行到一定程度后会被暂停,以便在未来某个时间点继续执行,这种情况下,同一时间只有一段代码在执行。ArkTS通过Promise和async/await提供异步并发能力,适用于单次I/O任务的开发场景。详细请参见使用异步并发能力
  • 多线程并发允许在同一时间段内同时执行多段代码。在UI主线程继续响应用户操作和更新UI的同时,后台线程也能执行耗时操作,从而避免应用出现卡顿。ArkTS通过TaskPoolWorker提供多线程并发能力,适用于耗时任务等并发场景。详细请参见多线程并发概述

并发多线程场景下,不同并发线程间需要进行数据通信,不同类别对象的传输方式存在差异,包括拷贝或内存共享等。


并发能力在多种场景中都有应用,其中包括异步并发任务耗时任务CPU密集型任务I/O密集型任务同步任务等)、长时任务常驻任务等。开发者可以根据不同的任务诉求和场景,选择相应的并发策略进行优化和开发,也可以具体查看应用多线程开发实践案例

二、异步并发 (Promise和async/await)

Promise和async/await提供异步并发能力,是标准的JS异步语法。异步代码会被挂起并在之后继续执行,同一时间只有一段代码执行,适用于单次I/O任务的场景开发,例如一次网络请求、一次文件读写等操作。无需另外启动线程执行。


异步语法是一种编程语言的特性,允许程序在执行某些操作时不必等待其完成,而是可以继续执行其他操作。

三、Promise

Promise是一种用于处理异步操作的对象,可以将异步操作转换为类似于同步操作的风格,以方便代码编写和维护。Promise提供了一个状态机制来管理异步操作的不同阶段,并提供了一些方法来注册回调函数以处理异步操作的成功或失败的结果。


Promise有三种状态:pending(进行中)、fulfilled(已完成)和rejected(已拒绝)。Promise对象创建后处于pending状态,并在异步操作完成后转换为fulfilled或rejected状态。


最基本的用法是通过构造函数实例化一个Promise对象,同时传入一个带有两个参数的函数,通常称为executor函数。executor函数接收两个参数:resolve和reject,分别表示异步操作成功和失败时的回调函数。例如,以下代码创建了一个Promise对象并模拟了一个异步操作:

const promise: Promise<number> = new Promise((resolve: Function, reject: Function) => {
  setTimeout(() => {
    const randomNumber: number = Math.random();
    if (randomNumber > 0.5) {
      resolve(randomNumber);
    } else {
      reject(new Error('Random number is too small'));
    }
  }, 1000);
})

上述代码中,setTimeout函数模拟了一个异步操作,并在1秒钟后随机生成一个数字。如果随机数大于0.5,则执行resolve回调函数并将随机数作为参数传递;否则执行reject回调函数并传递一个错误对象作为参数。

Promise对象创建后,可以使用then方法和catch方法指定fulfilled状态和rejected状态的回调函数。then方法可接受两个参数,一个处理fulfilled状态的函数,另一个处理rejected状态的函数。只传一个参数则表示当Promise对象状态变为fulfilled时,then方法会自动调用这个回调函数,并将Promise对象的结果作为参数传递给它。使用catch方法注册一个回调函数,用于处理“失败”的结果,即捕获Promise的状态改变为rejected状态或操作失败抛出的异常。例如:

import { BusinessError } from '@kit.BasicServicesKit';

promise.then((result: number) => {
 console.info(`Random number is ${result}`);
}).catch((error: BusinessError) => {
 console.error(error.message);
});

上述代码中,then方法的回调函数接收Promise对象的成功结果作为参数,并将其输出到控制台上。如果Promise对象进入rejected状态,则catch方法的回调函数接收错误对象作为参数,并将其输出到控制台上。

效果图
在这里插入图片描述

四、async/await

async/await是一种用于处理异步操作的Promise语法糖,使得编写异步代码变得更加简单和易读。通过使用async关键字声明一个函数为异步函数,并使用await关键字等待Promise的解析(完成或拒绝),以同步的方式编写异步操作的代码。


async函数是一个返回Promise对象的函数,用于表示一个异步操作。在async函数内部,可以使用await关键字等待一个Promise对象的解析,并返回其解析值。如果一个async函数抛出异常,那么该函数返回的Promise对象将被拒绝,并且异常信息会被传递给Promise对象的onRejected()方法。


下面是一个使用async/await的例子,其中模拟了一个以同步方式执行异步操作的场景,该操作会在3秒钟后返回一个字符串。

async function myAsyncFunction(): Promise<string> {
  const result: string = await new Promise((resolve: Function) => {
    setTimeout(() => {
      resolve('Hello, world!');
    }, 3000);
  });
  console.info(result); // 输出: Hello, world!
  return result;
}

@Entry
@Component
struct Index {
  @State message: string = 'Hello World';
  build() {
    Row() {
      Column() {
        Text(this.message)
          .fontSize(50)
          .fontWeight(FontWeight.Bold)
          .onClick(async () => {
            let res = await myAsyncFunction();
            console.info("res is: " + res);
          })
      }
      .width('100%')
    }
    .height('100%')
  }
}

效果图
在这里插入图片描述

在上述示例代码中,使用了await关键字来等待Promise对象的解析,并将其解析值存储在result变量中。


需要注意的是,由于要等待异步操作完成,因此需要将整个操作包在async函数中,并搭配await关键字使用。除了在async函数中使用await外,还可以使用try/catch块来捕获异步操作中的异常。

async function myAsyncFunction(): Promise<void> {
  try {
    const result: string = await new Promise((resolve: Function) => {
      resolve('Hello, world!');
    });
  } catch (e) {
    console.error(`Get exception: ${e}`);
  }
}

myAsyncFunction();

五、异步并发 (Promise和async/await)示例完整代码

TestPromiseAsyncAwait.ets

import { hilog } from '@kit.PerformanceAnalysisKit';
import { BusinessError } from '@kit.BasicServicesKit';

const TAG: string = 'TestPromiseAsyncAwait';
const DOMAIN_NUMBER: number = 0xFF00;

// 异步并发 (Promise和async/await) https://developer.huawei.com/consumer/cn/doc/harmonyos-guides-V5/async-concurrency-overview-V5
function testPromise() {
  const promise: Promise<number> = new Promise((resolve: Function, reject: Function) => {
    setTimeout(() => {
      const randomNumber: number = Math.random();
      if (randomNumber > 0.5) {
        resolve(randomNumber);
      } else {
        reject(new Error('Random number is too small'));
      }
    }, 1000);
  })

  promise.then((result: number) => {
    console.info(`promise.then Random number is ${result}`);
  }).catch((error: BusinessError) => {
    console.error(error.message);
  });
}

async function myAsyncFunction(): Promise<string> {
  const result: string = await new Promise((resolve: Function) => {
    setTimeout(() => {
      resolve('Hello, world!');
    }, 3000);
  });
  console.info(result); // 输出: Hello, world!
  return result;
}

async function myAsyncFunction2(): Promise<void> {
  try {
    const result: string = await new Promise((resolve: Function) => {
      resolve('Hello, world!');
    });
  } catch (e) {
    console.error(`Get exception: ${e}`);
  }
}

myAsyncFunction();

@Entry
@Component
struct TestPromiseAsyncAwait {
  build() {
    Column() {
      Button('测试Promise')
        .fontColor(Color.Black)
        .fontWeight(FontWeight.Normal)
        .fontSize(16)
        .margin({ top: 20 })
        .onClick((event: ClickEvent) => {
          testPromise()
        })
      Button('测试async/await ')
        .fontColor(Color.Black)
        .fontWeight(FontWeight.Normal)
        .fontSize(16)
        .margin({ top: 20 })
        .onClick((event: ClickEvent) => {
          let result = myAsyncFunction();
          console.log(`myAsyncFunction result is ${result}`);

          // myAsyncFunction2();
        })
    }
    .height('100%')
    .width('100%')
  }
}

标签:异步,并发,await,HarmonyOS,Promise,result,async
From: https://blog.csdn.net/ChinaDragon10/article/details/144083934

相关文章

  • HarmonyOS Next 与 iOS 开发融合之道
    本文旨在深入探讨华为鸿蒙HarmonyOSNext系统(截止目前API12)与iOS开发的融合相关技术细节,基于实际开发实践进行总结。主要作为技术分享与交流载体,难免错漏,欢迎各位同仁提出宝贵意见和问题,以便共同进步。本文为原创内容,任何形式的转载必须注明出处及原作者。第一章:异同点分析一......
  • HarmonyOS Next 智慧交通出行平台开发实践
    本文旨在深入探讨华为鸿蒙HarmonyOSNext系统(截止目前API12)在智慧交通出行平台开发中的应用,基于实际开发实践进行总结。主要作为技术分享与交流载体,难免错漏,欢迎各位同仁提出宝贵意见和问题,以便共同进步。本文为原创内容,任何形式的转载必须注明出处及原作者。第一章:平台规划与......
  • HarmonyOS Next 企业级移动办公应用构建
    本文旨在深入探讨华为鸿蒙HarmonyOSNext系统(截止目前API12)在企业级移动办公应用构建中的应用,基于实际开发实践进行总结。主要作为技术分享与交流载体,难免错漏,欢迎各位同仁提出宝贵意见和问题,以便共同进步。本文为原创内容,任何形式的转载必须注明出处及原作者。第一章:应用场景......
  • 超详细 HarmonyOS 开发教程之开发环境搭建指南
    HarmonyOS开发环境搭建指南:DevEcoStudio安装教程一、系统要求操作系统:Windows1064位或更高版本RAM:至少8GB,推荐16GB硬盘空间:至少10GB可用空间处理器:IntelCorei5或更高配置二、安装步骤1.下载DevEcoStudio2.访问华为开发者联盟官网:https://developer.harmonyos.com......
  • HarmonyOS开发者社区有奖征文二期活动开启!
    HarmonyOS开发者社区有奖征文活动第二期如约而至!在上一期的基础上,我们精心策划了更多样化的主题,旨在为开发者们提供一个更广阔的交流平台。无论您是想探讨HarmonyOS的技术细节,还是分享您的开发经验,或是记录您与HarmonyOS的点滴成长,这里都是您发声的舞台。让我们共同期待您的精......
  • HarmonyOS-初级(三)
    文章目录构建简单页面构建丰富的页面......
  • HarmonyOS Next 分布式开发实战
    本文旨在深入探讨华为鸿蒙HarmonyOSNext系统(截止目前API12)的分布式开发相关技术细节,基于实际开发实践进行总结。主要作为技术分享与交流载体,难免错漏,欢迎各位同仁提出宝贵意见和问题,以便共同进步。本文为原创内容,任何形式的转载必须注明出处及原作者。第一章:分布式概念......
  • HarmonyOS Next 应用性能优化秘籍
    本文旨在深入探讨华为鸿蒙HarmonyOSNext系统(截止目前API12)应用性能优化的相关技术细节,基于实际开发实践进行总结。主要作为技术分享与交流载体,难免错漏,欢迎各位同仁提出宝贵意见和问题,以便共同进步。本文为原创内容,任何形式的转载必须注明出处及原作者。第一章:性能优化......
  • 深入 HarmonyOS Next 系统能力调用
    本文旨在深入探讨华为鸿蒙HarmonyOSNext系统(截止目前API12)的系统能力调用相关技术细节,基于实际开发实践进行总结。主要作为技术分享与交流载体,难免错漏,欢迎各位同仁提出宝贵意见和问题,以便共同进步。本文为原创内容,任何形式的转载必须注明出处及原作者。第一章:系统能力......
  • HarmonyOS Next 与安卓开发对比及迁移指南
    本文旨在深入探讨华为鸿蒙HarmonyOSNext系统(截止目前API12)与安卓开发的对比,并提供迁移指南。基于实际开发实践进行总结,主要作为技术分享与交流载体,难免错漏,欢迎各位同仁提出宝贵意见和问题,以便共同进步。本文为原创内容,任何形式的转载必须注明出处及原作者。第一章:技术......