鸿蒙分布式理念?(个人认为理解就好)
鸿蒙操作系统的分布式理念主要体现在其独特的"流转"能力和相关的分布式操作上。在鸿蒙系统中,"流转"是指涉多端的分布式操作,它打破了设备之间的界限,实现了多设备间的联动。这种理念允许用户的应用程序在不同的设备上实现无缝流转,例如从手机到平板,或者从平板到电视,从而提供更加灵活和个性化的用户体验。
具体来说,鸿蒙的分布式理念包括以下几个关键方面:
-
设备互联 :鸿蒙系统通过分布式组网能力,使得不同的设备可以相互感知和连接,形成一个超级终端。这样,设备之间可以互相补充,共同为用户提供服务。
-
应用场景扩展 :分布式操作不仅限于设备之间的简单数据传输,还涵盖了多种复杂的场景,如跨设备编辑、多设备协同健身、多屏游戏等。这些场景都是通过设备间的紧密合作来实现的。
-
用户体验优化 :鸿蒙的分布式理念始终以用户为中心,通过提供更广泛的应用场景和产品视角,强化产品的优势,实现体验升级。例如,用户可以在一个设备上开始任务,在另一个设备上继续,无缝衔接。
-
开发者的机遇 :对于开发者而言,鸿蒙的分布式理念开辟了新的可能性。它允许开发者利用多设备协同的特点,开发出更为创新和有趣的应用,同时也提高了应用的可访问性和可用性。
总之,鸿蒙的分布式理念是通过其独特的技术和设计,实现多设备间的无缝协作,从而提升用户的日常生活和工作效率。这一理念正在推动智能设备行业向更加开放和互联的方向发展。
UIAbility的启动模式?
-
Singleton(单实例模式)
- 在这种模式下,系统中只存在一个UIAbility的实例 。即使多次调用
startAbility()
方法,系统也只会复用现有的实例,不会创建新的实例。这使得singleton模式适用于需要共享数据或资源的场景。 - 配置方法:在
module.json5
配置文件中,将launchType
字段设置为singleton
。
- 在这种模式下,系统中只存在一个UIAbility的实例 。即使多次调用
-
Multiton(多实例模式)
- 与singleton模式相反,multiton模式允许每次调用
startAbility()
方法时都创建一个新的UIAbility实例。这适用于需要独立的数据隔离或频繁创建销毁实例的场景。 - 配置方法:在
module.json5
配置文件中,将launchType
字段设置为multiton
。
- 与singleton模式相反,multiton模式允许每次调用
-
Specified(指定实例模式)
- 这种模式适用于需要精细控制实例行为的场景。例如,可以在应用中创建多个UIAbility实例,但希望重复打开同一实例时只使用同一个实例。
- 配置方法:在
module.json5
配置文件中,将launchType
字段设置为specified
,并在启动UIAbility时在Want的parameters字段中设置唯一的Key值来标识实例 。
RPC通信?
UIAbility在鸿蒙(HarmonyOS)中可以通过RPC(Remote Procedure Call)进行进程间通信。以下是UIAbility进行RPC通信的具体方式:
-
建立连接 : UIAbility可以通过
connectServiceExtensionAbility
方法连接到一个服务。这个方法需要一个Want
对象,该对象指定了要连接的服务的bundle名和ability名。例如:TypeScriptlet want: Want = { bundleName: "com.ohos.server", abilityName: "com.ohos.server.EntryAbility", }; let connectionId = context.connectServiceExtensionAbility(want, connect);
这里
connect
是一个包含了连接回调的选项对象,它定义了如何处理连接成功、断开连接和连接失败的情况。 -
通信过程 :
- 在连接成功后,可以通过
onConnect
回调获取到远程对象的代理,这个代理可以用来调用远程服务的方法。 - 如果需要监控远程服务的生死状态,可以注册死亡通知。这通过
registerDeathRecipient
方法实现,当远程服务消亡时,会调用onRemoteDied
方法。
- 在连接成功后,可以通过
-
关闭连接 : 当不再需要与服务通信时,应该注销死亡通知,并断开与服务的连接。这可以通过调用
unregisterDeathRecipient
和断开连接来实现。
以上步骤展示了UIAbility如何通过RPC进行进程间通信的基本流程。这种方式允许UIAbility与其他应用或服务进行数据交换和功能调用,是实现复杂功能和交互的重要手段。
进程通信?
在鸿蒙(HarmonyOS)中,UIAbility可以通过多种方式与其他Ability或服务进行进程间通信(IPC)。以下是一些主要的通信方式:
- 公共事件(Common Events) :
-
UIAbility可以通过发送和接收公共事件来与其他Ability或服务进行通信。这适用于不需要即时响应的广播类型通信。
-
示例代码 :
TypeScriptimport { commonEventManager } from '@kit.BasicServicesKit'; function publishEventWithData() { let options: commonEventManager.CommonEventPublishData = { code: 1, data: "ContactData" // 带敏感数据发送 }; commonEventManager.publish("MyCommonEvent", options, (err) => { if (err.code) { console.error("publish event error: " + err.code + ", " + err.message + ", " + err.name + ", " + err.stack); } else { console.info("publish event with data Succeeded"); } }); }
- 文件描述符传递(File Descriptor Passivation) :
-
在某些情况下,UIAbility可能需要与子进程进行通信,这时可以通过传递文件描述符来共享数据或资源。
-
示例代码 :
TypeScriptimport { ChildProcessArgs, childProcessManager } from '@kit.AbilityKit'; import fs from '@ohos.file.fs'; let context = getContext(this) as common.UIAbilityContext; let path = context.filesDir + "/test.txt";
以上两种方式都可以实现在不同的Ability或服务之间的通信,选择哪种方式取决于具体的应用需求和开发者的偏好。请注意,在使用公共事件时,应确保敏感数据的安全性,避免因权限设置不当导致的数据泄露。
线程通信?
鸿蒙操作系统中,线程间通信是一个关键的并发编程特性。在鸿蒙的ArkTS环境中,主要通过以下几种方式支持线程间通信:
- TaskPool 和 Worker :这两种机制都允许数据在不同的Worker线程之间进行通信。TaskPool 自行管理线程数量,适合执行耗时操作,并支持调度优先级和负载均衡 。Worker线程也用于执行耗时操作,但其生命周期由开发者自行维护 。这两种方式都可以通过消息传递来进行线程间的通信。
- EventHub :这是一个用于线程内数据通信的机制,允许组件如UIAbility和UI组件在同一主线程中进行数据同步 。它支持事件的订阅、取消订阅和触发,从而实现线程内的数据交换。
- Emitter :这是一种事件驱动的线程间通信方式,允许应用程序在不同线程或同一线程内订阅、发布和取消事件。通过维护一个事件队列,Emitter能够异步地分发事件给订阅者,支持通过设置不同的回调方法来处理各种事件 。
这些通信机制各有特点,适用于不同的应用场景和需求,开发者可以根据实际需要选择最适合的通信方式来优化应用的性能和响应速度。
项目怎么做性能优化的?
在鸿蒙(HarmonyOS)项目中进行性能优化是一个系统性的过程,主要包括以下几个关键步骤:
-
现场复现 :这是性能优化的第一步,需要在具体的运行环境中复现存在的问题,如应用卡顿、响应迟缓等,以便更准确地捕捉和分析问题。
-
问题分析 :通过使用各种性能分析工具,如DevEco Profiler和HiDumper,收集和分析数据,以定位引起性能问题的代码部分。例如,可以使用DevEco Profiler中的Frame Profiler工具来分析应用卡顿的原因,或使用HiDumper来查看内存和CPU的使用情况 。
-
确定解决方案 :根据问题分析的结果,制定具体的优化方案 。这可能涉及到代码的修改、资源的优化配置或是算法的改进。(可能相听这个)
-
性能测试 :优化实施后,需要对应用进行性能测试,确保优化措施有效提高了应用的性能 。可以使用DevEco Profiler或其他性能测试工具来验证优化效果 。
在整个优化过程中,开发者需要注意监控和分析应用的性能指标,如帧率、内存使用、CPU占用等,这些指标可以帮助开发者更好地理解应用的运行状态和性能瓶颈 。此外,合理的使用缓存管理和组件复用技术,也可以显著提升应用的性能,比如通过设置LazyForEach的cachedCount来优化长列表的加载性能。
通过上述步骤和技术的应用,可以在鸿蒙项目中有效地进行性能优化,提升应用的响应速度和稳定性,从而改善用户体验。
后台任务类型?对应的使用场景?
以下是鸿蒙系统中主要的后台任务类型:
-
短时任务 :
- 概念 :适用于实时性要求高、耗时不长的任务,如小文件下载、缓存、信息发送等。
- 应用场景 :当应用短暂切换到后台时,可以通过申请短时任务来避免进程被挂起 。
- 实现方式 :通过
ApplicationContext.on('applicationStateChange')
注册应用前后台变化的监听,当应用退至后台时,触发onApplicationBackground()
回调函数,在此回调函数中申请短时任务 。
-
长时任务 :
- 概念 :适用于长时间运行在后台的任务,如数据传输、音频播放、录音等。
- 应用场景 :需要在后台持续执行的任务,如数据处理、软件更新等。
- 实现方式 :在应用的后台服务中申请长时任务,确保任务在应用退至后台后仍能继续运行。
-
延迟任务 :
- 概念 :适用于实时性要求不高的任务,可以延迟执行,如数据处理、信息收集等。
- 应用场景 :适用于不需要即时响应的后台处理任务。
- 实现方式 :设置延迟任务的触发条件,当条件满足时,系统会将任务放入执行队列,根据系统资源情况统一调度执行。
-
代理提醒 :
- 概念 :系统代理应用做出相应的提醒,如闹钟、倒计时、日历等。
- 应用场景 :适用于需要系统级提醒的服务,如会议提醒、服药提醒等。
- 实现方式 :在应用中设置提醒服务,当达到预设时间或条件时,系统代理应用执行提醒操作。
每种后台任务类型都有其适用的场景和相应的实现方式,开发者可以根据应用的具体需求选择合适的后台任务类型,以确保应用在后台的稳定运行和高效执行。
HAP、HAR、HSR三种包的区别?
HAP、HAR和HSP是鸿蒙操作系统中用于应用开发和部署的三种不同类型的包,它们各有特定的功能和使用场景。
-
HAP(Harmony Ability Package)
- HAP是应用安装和运行的基本单元,可以独立安装和运行 。它主要包括代码、资源、第三方库和配置文件等。
- HAP分为entry和feature两种类型:entry作为应用的入口,提供基础功能;feature则作为应用能力的扩展,可根据用户需求和设备类型进行选择性安装。
- 在单HAP场景中,应用可以直接由一个entry包构成;而在多HAP场景中,可以由一个entry包和多个feature包组成,以应对更复杂的功能需求。
-
HAR(HarmonyOS Archive)
- HAR是一种静态共享包,主要用于编译态复用,支持应用内的共享以及发布后供其他应用使用 。
- HAR适用于作为二方库或三方库发布到不同的仓库中,供公司内部或其他应用使用。
- 编译HAR时,建议开启混淆能力以保护代码资产。多包引用相同的HAR时,会导致应用包大小的增加。
-
HSP(HarmonyOS Shared Package)
- HSP是动态共享包,主要用于运行时复用。当多包同时引用同一个共享包时,使用HSP可以避免HAR造成的多包间代码和资源的重复拷贝,从而减小应用包大小 。
- HSP不支持循环依赖,也不支持依赖传递 。
总结来说,HAP是应用的功能模块,可以独立安装和运行;HAR和HSP则是分别为编译态和运行时设计的共享包,用于代码和资源的复用 2。开发者可以根据实际的应用需求和性能考虑,选择合适的包类型进行开发和部署。
多线程的区别,TaskPool和Worker?
TaskPool和Worker都是多线程并发解决方案,旨在提高应用程序的性能和响应能力 。它们都允许程序在多个线程上执行耗时任务,从而避免阻塞主线程。以下是TaskPool和Worker在实现特点和适用场景上的对比:
实现特点对比
- 参数传递 :
- TaskPool:支持直接传递参数,无需封装,默认进行transfer 。
- Worker:需要消息对象作为唯一参数,要求开发者自行封装。
- 方法调用 :
- TaskPool:可以直接将方法传入调用。
- Worker:在Worker线程中进行消息解析并调用对应方法 。
- 返回值 :
- TaskPool:异步调用后默认返回 。
- Worker:需要在onmessage中解析赋值 。
- 生命周期管理 :
- TaskPool:自行管理生命周期,无需关心任务负载高低 。
- Worker:开发者自行管理Worker的数量及生命周期 。
- 任务执行特性 :
- TaskPool:支持任务优先级设置、任务取消、任务延时执行和设置任务依赖关系 。
- Worker:不支持这些高级特性。
适用场景对比
- TaskPool :由于支持自动扩缩容和任务优先级设置,适合需要高度管理和优化的环境,如大型应用的多个模块包含多个耗时任务。
- Worker :适合执行长时间占据线程的任务,如后台进行长时间的预测算法训练等CPU密集型任务。
总结来说,TaskPool提供了更多的管理功能和灵活性,适合复杂的多任务管理场景;而Worker则更适合执行单一的、长时间的任务。开发者可以根据实际的应用需求和性能考量选择合适的多线程解决方案。
Navigational和router的区别?
Navigation和Router是HarmonyOS中支持的两种不同的路由机制,它们在易用性、功能和性能上有明显的区别 。以下是这两者的主要对比:
易用性
- Navigation :具有天然的标题、内容和回退按钮的功能联动,页面由组件构成,易于实现共享元素的转场 。
- Router :需要开发者自行定义上述功能,页面配置在单独的page中,通过@Entry进行标识 。
功能
- Navigation :支持一多跳转,没有路由数量限制,可以获取路由栈NavPathStack,并可以在模态对话框中定义路由 。开发者可以自定义复杂的动效和属性设置 。
- Router :不支持一多跳转,路由数量限制为32个,页面使用@Entry进行修饰,不支持模态框中的路由定义 。
性能
- Navigation :传递参数性能更优,通过引用传递,可以配合动态加载实现组件动态加载 。
- Router :通过深拷贝完成参数传递,页面在当前模块加载时会生成全量页面 。
结构和能力对比
- Navigation :每个页面承载在一个page里,通过NavDestination容器实现基于组件的页面跳转 。支持跳转指定页面、跳转HSP和HAR中页面、跳转传参、获取指定页面参数等 。
- Router :每个页面配置在一个单独的page中,支持跳转指定页面、跳转HSP和HAR中页面、跳转传参等,但不支持获取指定页面参数 。
根据您的应用场景和需求,您可以选择更适合的路由方案。一般来说,Navigation由于其更高的灵活性和扩展性,被推荐为首选的路由框架。
LazyForEach的工作原理?
LazyForEach是一种用于实现数据懒加载的技术,主要用于大规模数据集的处理,如长列表或网格。它的基本原理是在需要的时候才加载数据或资源,而不是一次性加载所有数据,从而优化性能和提升用户体验 。
工作原理
- 数据按需加载 :LazyForEach允许开发者根据用户的交互(如滚动页面)动态加载数据。这意味着只有进入屏幕可视区域的数据才会被加载,这大大减少了内存的使用和提升了应用性能。
- 组件树挂载和页面渲染 :当数据被加载时,LazyForEach会根据数据动态创建和销毁组件,从而减轻了页面初次加载时的负担 。这种动态组件管理也有助于提高应用的响应速度。
关键组件
- 数据源(DataSource) :开发者需要提供一个数据源,这是一个
IDataSource
类型的对象,用于存储和管理数据。 - 键值生成函数(KeyGenerator) :这是一个用于为每个数据项生成唯一键值的函数,帮助LazyForEach跟踪和管理组件。
- 子组件生成函数(ItemGenerator) :这个函数根据键值和数据源为每个数据项创建组件 。
性能优化
- 缓存策略 :LazyForEach可以通过设置
cachedCount
来指定缓存的组件数量,这样可以减少因频繁创建和销毁组件而导致的性能损耗。 - 组件复用 :LazyForEach支持组件复用,即在数据项从屏幕中消失后,其对应的组件不会立即被销毁,而是被存储在缓存池中,以便再次使用。
通过这些机制,LazyForEach能够在保证应用性能的同时,提供流畅的用户体验。特别是在处理大量数据时,能够显著减少内存使用和提升应用响应速度。
H5是如何跟鸿蒙通信的?
在鸿蒙(HarmonyOS)系统中,H5页面与原生应用的通信主要通过"Native PostWebMessage"机制实现。这种机制允许H5页面和原生应用在不同的运行时环境中进行通信,而无需进行环境切换,从而提高了通信的效率和应用的响应速度。
通信机制
"Native PostWebMessage"是一种基于消息的通信方式,它允许消息的发送和接收在非UI线程上运行,这样可以避免UI阻塞,确保用户体验的流畅性。目前,该机制支持的数据类型包括string和buffer。
应用场景
这种通信方式特别适用于那些使用ArkTS和C++混合开发的应用,或者那些架构类似于小程序的应用。通过使用ArkWeb在Native侧提供的APIs,如ArkWeb_ControllerAPI、ArkWeb_WebMessageAPI和ArkWeb_WebMessagePortAPI,开发者可以实现在C++环境中与H5页面的直接通信。
实现步骤
-
绑定ArkWeb组件 :在ArkTS侧,开发者需要声明一个ArkWeb组件,并通过Node-API将一个唯一的webTag传递到应用的C++侧 1。这个webTag将用于标识ArkWeb组件,以便在Native侧进行通信 。
-
获取API结构体 :在C++侧,开发者需要首先获取API结构体,这是通过函数
OH_ArkWeb_GetNativeAPI
实现的。根据类型的 different,可以获取不同的函数指针结构体,这些结构体包含了实现PostWebMessage功能所需的Native API。
通过上述步骤,H5页面就能够与鸿蒙系统的原生应用进行有效的数据交换和事件处理,实现了丰富的交互体验和高效的数据处理能力。
沉浸式是如何实现的?
沉浸式页面开发在鸿蒙操作系统中主要通过两种方法实现:设置窗口全屏模式和扩展组件安全区域 1。这两种方法都可以实现将应用页面延伸到状态栏和导航栏的效果,从而提供更大的视觉空间和更好的用户体验。
方案一:设置窗口全屏模式
这种方法通过使用 Window.setWindowLayoutFullScreen()
方法来实现。它将窗口设置为全屏模式,使得应用界面能够占据整个屏幕,包括状态栏和导航栏区域 1。这样,用户可以看到更多的内容,而不会被系统栏所遮挡。
TypeScript
// 设置窗口全屏,实现沉浸式效果
windowClass.setWindowLayoutFullScreen(true).then(() => {
console.info('Succeeded in setting the window layout to full-screen mode.');
}).catch((e: BusinessError) => {
console.error('Failed to set the window layout to full-screen mode. Cause:' + JSON.stringify(e));
});
方案二:扩展组件安全区域
第二种方法是通过设置组件的 expandSafeArea
属性来扩展组件的安全区域到状态栏和导航栏 。这种方法只影响特定的组件,而不影响页面上的其他组件。它允许开发者更精细地控制哪些部分 of 应用应该延伸到系统栏下。
TypeScript
@Column
@Component
struct Example {
build() {
Column() {
Row() {
Text('Top Row')
.fontSize(40)
.textAlign(TextAlign.Center)
.width('100%')
}
.backgroundColor('F08080')
// 设置顶部绘制延伸到状态栏
.expandSafeArea([SafeAreaType.SYSTEM], [SafeAreaEdge.TOP])
}
}
}
Want显式与隐式的区别?
显式Want和隐式Want是HarmonyOS中用于启动Ability的两种不同方式,它们的主要区别在于如何指定待启动的Ability以及使用的场景。
显式Want
显式Want是指在Want对象中明确指定了待启动Ability的bundleName
、abilityName
和moduleName
1。这种方式可以直接匹配到指定的Ability,适用于已知具体Ability信息的场景。显式Want的优点是安全性较高,因为它确保了只能启动预设的Ability,但缺点是灵活性较低,不适用于动态或不确定Ability信息的场景。
- 显式Want
TypeScript
import Want from '@ohos.application.Want';
let want: Want = {
'deviceId': '',
'bundleName': 'com.example.myapplication',
'abilityName': 'EntryAbility',
};
隐式Want
隐式Want则是在Want对象中不直接指定具体的Ability名称,而是通过action
、entities
等字段来描述待启动Ability应执行的操作和应具备的特性。隐式Want适用于不知道具体Ability名称或者需要动态匹配Ability的场景。它的优点是灵活性高,可以匹配多个符合特定条件的Ability,但缺点是如果系统中存在多个匹配的Ability,可能会导致不确定性。
- 隐式Want :
TypeScript
import Want from '@ohos.application.Want';
let want: Want = {
'action': 'view',
'entities': ['browser']
};
Axios实现图片上传的?
在使用Axios进行图片上传时,通常需要将图片数据封装在FormData中,然后通过Axios发送POST请求。以下是基本的实现步骤:
-
创建FormData对象 :首先创建一个FormData实例,并将图片文件添加到这个对象中。通常,可以通过HTML的input元素获取用户选择的图片文件。
TypeScriptconst formData = new FormData(); formData.append('image', file); //假设file是用户选择的图片文件
-
配置Axios请求 :使用Axios发送POST请求,将FormData作为请求体发送。需要注意设置请求头的
Content-Type
为multipart/form-data
,这是因为图片文件需要在这种类型的数据中传输。TypeScriptimport axios from 'axios'; const config = { headers: { 'Content-Type': 'multipart/form-data' } }; axios.post('/api/upload', formData, config) .then(response => { console.log('图片上传成功'); }) .catch(error => { console.error('图片上传失败', error); });
音视频的开发使用过那些API?分别有那些状态?
AVRecorder(音视频录制器)
AVRecorder主要用于视频的录制,它集成了音频捕获、音频编码、视频编码和音视频封装功能 。开发者可以通过AVRecorder的state
属性来获取当前状态,或者使用on('stateChange')
方法来监听状态变化 。
状态包括:
- started :录制开始状态。
- paused :录制暂停状态。
- resumed :录制恢复状态。
- stopped :录制停止状态。
开发者应该严格遵循状态机的要求,例如只能在started
状态下调用pause()
接口,只能在paused
状态下调用resume()
接口 。
AVPlayer(音视频播放器)
AVPlayer则用于播放流媒体 。在使用前,需要声明ohos.permission.INTERNET
权限,并且使用支持的播放格式与协议 。
主要操作包括:
prepare()
:准备播放,进入prepared
状态,此时可以获取duration,设置音量 。play()
:开始播放。pause()
:暂停播放。seek()
:跳转到视频的特定位置。stop()
:停止播放。release()
:销毁实例,退出播放 。
此外,AVPlayer还支持监听缓冲状态和码率切换,帮助开发者优化播放体验。
通过这些API和状态的管理,开发者可以在鸿蒙系统上实现丰富的音视频功能。