【HarmonyOS Next】鸿蒙应用进程和线程详解

简介: 进程的定义:进程是系统进行资源分配的基本单位,是操作系统结构的基础。 在鸿蒙系统中,一个应用下会有三类进程:


##鸿蒙开发能力 ##HarmonyOS SDK应用服务##鸿蒙金融类应用 (金融理财#

一、前言

  1. 进程的定义:
    进程是系统进行资源分配的基本单位,是操作系统结构的基础。 在鸿蒙系统中,一个应用下会有三类进程
    (1) 主进程
    (2) ExtensionAbility进程,同一种类型的ExtensionAbility会放在一个进程里。例如FromExtensionAbility,创建了两个,也会在同一个进程里。【ExtensionAbility详情参见官方链接:ExtensionAbility组件
    (3) WebView渲染进程,用于网页容器渲染的进程。【这种设计提升了鸿蒙系统中arkWeb的网页容器渲染能力】
  2. 线程的定义:
    线程是操作系统进行运算调度的基本单位,是进程中的执行流,共享进程的资源。 鸿蒙系统中,以主进程举例,会有三种类型的线程:
    (1)主线程
    (2)TaskPool Worker线程
    (3)Worker线程
    后两者用于创建多线程,TaskPool Worker主要用于处理轻量级的耗时任务。Worker用于偏重的耗时任务。

二、进程处理:

  1. 进程的创建:
    如上图所示,三方应用可以创建XXExtensionAbility的形式,增加应用内的进程。但是Webview渲染进程和主进程的是不能创建增加。
  2. 跨进程通信:
    鸿蒙系统目前提供了两种方式实现跨进程通信,公共事件和Emitter。这两个方案外,startAbility也可传递一些信息。

公共事件主要是监听系统的事件,分为系统公共事件和自定义事件。三方应用主要通过自定义事件来通信。

import { commonEventManager } from '@kit.BasicServicesKit';
import { BusinessError } from '@kit.BasicServicesKit';
// 定义订阅者,用于保存创建成功的订阅者对象,后续使用其完成订阅及退订的动作
let subscriber: commonEventManager.CommonEventSubscriber;
// 订阅者信息
let subscribeInfo: commonEventManager.CommonEventSubscribeInfo = {
    events: ["event"]
};
// 创建订阅者回调
function createCB(err: BusinessError, commonEventSubscriber: commonEventManager.CommonEventSubscriber) {
  if (err != null) {
    console.error(`Failed to create subscriber. Code is ${err.code}, message is ${err.message}`);
  } else {
    console.info(`Succeeded in creating subscriber`);
    subscriber = commonEventSubscriber;
  }
}
// 创建订阅者
commonEventManager.createSubscriber(subscribeInfo, createCB);

Emitter的使用类似于EventHub,只不过在这个基础上,多了传递包裹的封装,添加了优先级和序号。也新增了once,监听一次的接口而已。

@Sendable
class Sample {
    constructor() {
        this.count = 100;
    }
    printCount() {
        console.info('Print count : ' + this.count);
    }
    count: number;
}
let callback = (eventData: emitter.GenericEventData<Sample>): void => {
   let storage: Sample = eventData.data!;
   storage.printCount();
}
// 收到eventId为"eventId"的事件后执行回调函数
emitter.on("eventId", callback);

三、线程处理:

1.线程的创建和线程间通信
如上所说,可以使用TaskPool Worker 和 Worker创建线程。并且配套会有双向通信的接口。
需要注意的是前者有性能要求,太过于耗时的操作,例如超过三分钟,就会无条件失败,这种耗时任务就要使用后者Worker来实现。不过后者又因为消耗系统资源,一个应用只能创建八个。

TaskPool Worker:

@Concurrent
function printArgs(args: number): number {
    console.info("printArgs: " + args);
    return args;
}
taskpool.execute(printArgs, 100).then((value: Object) => { // 100: test number
  console.info("taskpool result: " + value);
});

Worker:

// Worker.ets
import { worker, MessageEvents, ErrorEvent } from '@kit.ArkTS';
// 创建worker线程中与宿主线程通信的对象
const workerPort = worker.workerPort
// worker线程接收宿主线程信息
workerPort.onmessage = (e: MessageEvents): void => {
  // data:宿主线程发送的信息
  let data: number = e.data;
  // 往收到的buffer里写入数据
  const view = new Int8Array(data).fill(3);
  // worker线程向宿主线程发送信息
  workerPort.postMessage(view);
}
// worker线程发生error的回调
workerPort.onerror = (err: ErrorEvent) => {
  console.log("worker.ets onerror" + err.message);
}
// Index.ets
import { worker, MessageEvents, ErrorEvent } from '@kit.ArkTS';
@Entry
@Component
struct Index {
  @State message: string = 'Hello World';
  build() {
    Row() {
      Column() {
        Text(this.message)
          .fontSize(50)
          .fontWeight(FontWeight.Bold)
          .onClick(() => {
            // 宿主线程中创建Worker对象
            const workerInstance = new worker.ThreadWorker("entry/ets/workers/Worker.ets");
            // 宿主线程向worker线程传递信息
            const buffer = new ArrayBuffer(8);
            workerInstance.postMessage(buffer, [buffer]);
            // 宿主线程接收worker线程信息
            workerInstance.onmessage = (e: MessageEvents): void => {
              // data:worker线程发送的信息
              let data: number = e.data;
              console.info("main thread data is  " + data);
              // 销毁Worker对象
              workerInstance.terminate();
            }
            // 在调用terminate后,执行onexit
            workerInstance.onexit = (code) => {
              console.log("main thread terminate");
            }
            workerInstance.onerror = (err: ErrorEvent) => {
              console.log("main error message " + err.message);
            }
          })
      }
      .width('100%')
      .height('100%')
    }
  }
}

2.线程内通信
EventHub,GlobalThis,单例,AppStorage。都可实现线程内UI界面,UIAbility和业务类之间的通信。

目录
相关文章
|
8天前
|
监控 JavaScript 编译器
从“天书”到源码:HarmonyOS NEXT 崩溃堆栈解析实战指南
本文详解如何利用 hiAppEvent 监控并获取 sourcemap、debug so 等核心产物,剖析了 hstack 工具如何将混淆的 Native 与 ArkTS 堆栈还原为源码,助力开发者掌握异常分析方法,提升应用稳定性。
|
1月前
|
开发者 容器
鸿蒙应用开发从入门到实战(十四):ArkUI组件Column&Row&线性布局
ArkUI提供了丰富的系统组件,用于制作鸿蒙原生应用APP的UI,本文主要讲解Column和Row组件的使用以及线性布局的方法。
210 12
|
1月前
|
存储 人工智能 算法
鸿蒙HamonyOS应用上架手动签名与发布
鸿蒙HamonyOS应用上架手动签名与发布
143 4
鸿蒙HamonyOS应用上架手动签名与发布
|
1月前
|
API 数据处理
鸿蒙应用开发从入门到实战(十三):ArkUI组件Slider&Progress
ArkUI提供了丰富的系统组件,用于制作鸿蒙原生应用APP的UI,本文主要讲解滑块Slider和进度条Progress组件的使用。
118 1
|
1月前
|
JavaScript 开发者 索引
鸿蒙应用开发从入门到实战(九):ArkTS渲染控制
ArkTS拓展了TypeScript,可以结合ArkUI进行渲染控制,是的界面设计具有可编程性。本文简要描述鸿蒙应用开发中的条件渲染和循环渲染。
116 5
|
1月前
|
数据安全/隐私保护 开发者
鸿蒙应用开发从入门到实战(十一):ArkUI组件Text&TextInput
ArkUI提供了丰富的系统组件,用于制作鸿蒙原生应用APP的UI,本文主要讲解文本组件Text和TextInput的使用。
226 3
|
20天前
|
Java 测试技术 API
【JUC】(1)带你重新认识进程与线程!!让你深层次了解线程运行的睡眠与打断!!
JUC是什么?你可以说它就是研究Java方面的并发过程。本篇是JUC专栏的第一章!带你了解并行与并发、线程与程序、线程的启动与休眠、打断和等待!全是干货!快快快!
248 2
|
20天前
|
JSON 网络协议 安全
【Java】(10)进程与线程的关系、Tread类;讲解基本线程安全、网络编程内容;JSON序列化与反序列化
几乎所有的操作系统都支持进程的概念,进程是处于运行过程中的程序,并且具有一定的独立功能,进程是系统进行资源分配和调度的一个独立单位一般而言,进程包含如下三个特征。独立性动态性并发性。
86 1
|
20天前
|
JSON 网络协议 安全
【Java基础】(1)进程与线程的关系、Tread类;讲解基本线程安全、网络编程内容;JSON序列化与反序列化
几乎所有的操作系统都支持进程的概念,进程是处于运行过程中的程序,并且具有一定的独立功能,进程是系统进行资源分配和调度的一个独立单位一般而言,进程包含如下三个特征。独立性动态性并发性。
90 1
|
1月前
|
存储 缓存 5G
鸿蒙 HarmonyOS NEXT端云一体化开发-云存储篇
本文介绍用户登录后获取昵称、头像的方法,包括通过云端API和AppStorage两种方式,并实现上传头像至云存储及更新用户信息。同时解决图片缓存问题,添加上传进度提示,支持自动登录判断,提升用户体验。
118 1

热门文章

最新文章