本文旨在深入探讨华为鸿蒙HarmonyOS Next系统(截止目前API12)的技术细节,基于实际开发实践进行总结。主要作为技术分享与交流载体,难免错漏,欢迎各位同仁提出宝贵意见和问题,以便共同进步。本文为原创内容,任何形式的转载必须注明出处及原作者。

鸿蒙系统提供了两种并发能力:TaskPool 和 Worker。它们都基于 Actor 并发模型实现,但它们的使用场景和功能有所不同。

  • TaskPool:TaskPool 是一个多线程运行环境,它提供了任务的执行、取消、优先级设置等功能。TaskPool 适用于独立任务,例如计算密集型任务、I/O 密集型任务等。
  • Worker:Worker 是一个可以长时间运行的后台线程,它支持与宿主线程之间的消息传递。Worker 适用于长时间运行的任务,例如后台数据处理、模型训练等。

    TaskPool 和 Worker 的区别与使用场景

    特性TaskPoolWorker
    内存模型线程间隔离,内存不共享线程间隔离,内存不共享
    参数传递机制采用标准的结构化克隆算法(Structured Clone)进行序列化、反序列化,完成参数传递。支持 ArrayBuffer 转移和 SharedArrayBuffer 共享。采用标准的结构化克隆算法(Structured Clone)进行序列化、反序列化,完成参数传递。支持 ArrayBuffer 转移和 SharedArrayBuffer 共享。
    参数传递直接传递,无需封装,默认进行 transfer。消息对象唯一参数,需要自己封装。
    方法调用直接将方法传入调用。在 Worker 线程中进行消息解析并调用对应方法。
    返回值异步调用后默认返回。主动发送消息,需在 onmessage 解析赋值。
    生命周期TaskPool 自动管理生命周期,无需关心任务负载高低。开发者自行管理 Worker 的数量及生命周期。
    任务池个数上限自动管理,无需配置。同个进程下,最多支持同时开启 64 个 Worker 线程,实际数量由进程内存决定。
    任务执行时长上限3 分钟(不包含 Promise 和 async/await 异步调用的耗时,例如网络下载、文件读写等 I/O 任务的耗时),长时任务无执行时长上限。无限制。
    设置任务的优先级支持配置任务优先级。不支持。
    执行任务的取消支持取消已经发起的任务。不支持。
    线程复用支持。不支持。
    任务延时执行支持。不支持。
    设置任务依赖关系支持。不支持。
    串行队列支持。不支持。
    任务组支持。不支持。

    使用场景

  • TaskPool:适用于独立任务,例如计算密集型任务、I/O 密集型任务等。
  • Worker:适用于长时间运行的任务,例如后台数据处理、模型训练等。

    TaskGroup 的管理与任务优先级

    TaskGroup:TaskGroup 是一个任务集合,可以将多个任务添加到 TaskGroup 中,并一起执行。TaskGroup 支持配置任务的优先级。
    示例

    import { taskpool } from '@kit.ArkTS';
    @Concurrent
    function add(num1: number, num2: number): number {
      return num1 + num2;
    }
    @Concurrent
    function subtract(num1: number, num2: number): number {
      return num1 - num2;
    }
    async function concurrentFunc() {
      const task1 = new taskpool.Task(add, 1, 2);
      const task2 = new taskpool.Task(subtract, 3, 4);
      const group = new taskpool.TaskGroup();
      group.addTask(task1);
      group.addTask(task2);
      group.addTask(task1); // 添加重复任务
      await taskpool.execute(group, taskpool.Priority.HIGH);
    }

    任务优先级

  • Priority.IDLE:后台任务,优先级最低。
  • Priority.LOW:低优先级任务。
  • Priority.MEDIUM:中等优先级任务。
  • Priority.HIGH:高优先级任务。

    任务的添加与执行逻辑

    任务添加

    const task = new taskpool.Task(func, args);

    任务执行

    await taskpool.execute(task);

    任务取消

    taskpool.cancel(task);

    示例代码:通过 TaskPool 执行 CPU 密集型任务的示例

    以下是一个简单的示例,演示如何使用 TaskPool 执行 CPU 密集型任务:

    import { taskpool } from '@kit.ArkTS';
    @Concurrent
    function complexCalculation(data: ArrayBuffer): ArrayBuffer {
      // 执行复杂的计算操作
      return data;
    }
    async function concurrentCalculation() {
      const data = new ArrayBuffer(1024);
      const task = new taskpool.Task(complexCalculation, data);
      await taskpool.execute(task);
    }
    @Entry
    @Component
    struct Index {
      @State message: string = 'Hello World';
      build() {
    Row() {
      Column() {
        Text(this.message)
          .fontSize(50)
          .fontWeight(FontWeight.Bold)
          .onClick(async () => {
            await concurrentCalculation();
          })
          .width('100%');
      }
    }
    .height('100%');
      }
    }

    这段代码定义了一个名为 Index 的组件,并在组件中显示了一条文本消息 "Hello World"。点击按钮会执行 concurrentCalculation 函数,该函数创建一个并发任务并执行它。任务完成后,会在控制台输出结果。

    总结

    通过以上介绍,您可以了解到鸿蒙系统中的 TaskPool 和 Worker 并发能力的使用方法。TaskPool 和 Worker 都是基于 Actor 并发模型实现的,但它们的使用场景和功能有所不同。希望本文能够帮助您掌握鸿蒙系统中的并发编程技术,并开发出更优秀的鸿蒙应用。


SameX
1 声望2 粉丝