【HarmonyOS Next】鸿蒙应用常规面试题和答辩思路参考
一、充分了解岗位JD要求
根据招聘发布的岗位JD,进行自我匹配分析。了解基本要求和加分项,以及项目节奏和英文要求等。
- 技术不匹配的点,是否会影响应聘岗位
- 加分项自己是否掌握,是否有亮点,提前和招聘同步,在简历中加粗标明
- 对于学历和工作经验要求,是否符合。若自己技术能力强,在行业内有一定影响力或者优秀的开源项目,询问招聘人是否有绿色通道【很关键】
- 准备自己与岗位相关的技能证书和荣誉证明
- 根据项目节奏分析自己是否可适应,并且了解公司所在地与自己通勤成本
二、面试前期准备工作
1.了解是否会有背景调查环节,检查自己的个人材料,查漏补缺
2.询问招聘对接人,面试范围,获取有用的信息,充分准备复习
3.完善简历中描述的项目经验【这很关键】,要清楚面试的目的,是公司需要验证候选人的技能能力和项目真实程度。
4.将自己负责的项目中,较为复杂的解决方案。问题的发现,定位和解决完整过程进行梳理。【但是要小心被对方套方案,如果面试人的问题很简单,这里可以斟酌模糊回答。】
5.针对面试官说,你有什么想问的,要表达自己对于岗位的疑问和对于工作内容的求知欲。
三、面试题参考
标准的面试环节,会根据你应聘的岗位级别,有针对的询问候选人。例如初中高三种级别,询问的内容是不尽相同的。
1. 是否了解HarmonyOS和OpenHarmony的区别?
HarmonyOS 是华为基于 OpenHarmony 等开发的商用版本,OpenHarmony 是开源项目,二者在性质来源、技术实现等方面存在差异。
回答出差异点与来源即可。
2.介绍一下你自己负责鸿蒙开发的较为复杂的功能有哪些?
建议根据自己的实际项目经验来准备。因为如果不是自己的开发的功能,面试官逐步问到细节,会导致出问题。当然能力强无所谓。
复杂度亮眼的功能,突出自己的工作能力,学习能力和解决问题的能力即可。
3. 举例V1状态装饰器有什么?是做什么的?
在鸿蒙开发中,状态装饰器是 ArkTS 语言里用于管理组件状态的关键工具,在早期版本(V1)中有以下常见的状态装饰器及其作用,以下是一个完整的鸿蒙开发示例,展示了如何使用 @State、@Prop、@Link、@Provide 和 @Consume 这些 V1 状态装饰器:
// 祖先组件,使用 @Provide 提供数据
struct AncestorComponent { sharedMessage: string = '这是共享消息' parentCount: number = 0build() {Column({ space: 50 }) {// 父组件,传递数据给子组件ParentComponent({ parentValue: $parentCount })// 后代组件,消费共享数据DescendantComponent()}}
}// 父组件
struct ParentComponent { parentValue: number localCount: number = 0build() {Column({ space: 20 }) {Text(`父组件本地计数: ${this.localCount}`)Button('增加父组件本地计数').onClick(() => {this.localCount++})Text(`从祖先组件传递过来的计数: ${this.parentValue}`)Button('增加祖先组件传递过来的计数').onClick(() => {this.parentValue++})// 子组件,接收父组件传递的数据ChildComponent({propValue: this.localCount,linkValue: $localCount})}}
}// 子组件
struct ChildComponent { propValue: number linkValue: numberbuild() {Column({ space: 20 }) {Text(`通过 接收的父组件数据: ${this.propValue}`)Text(`通过 绑定的父组件数据: ${this.linkValue}`)Button('增加通过 @Link 绑定的数据').onClick(() => {this.linkValue++})}}
}// 后代组件,使用 @Consume 消费共享数据
struct DescendantComponent { sharedMessage: stringbuild() {Column({ space: 20 }) {Text(`通过 消费的共享消息: ${this.sharedMessage}`)}}
}
struct MainPage {build() {Column({ space: 50 }) {// 渲染祖先组件AncestorComponent()}}
}
4. V2状态装饰器主要解决了什么问题?都有什么?举几个例子即可
在鸿蒙开发中,ArkTS 从 V1 到 V2 状态装饰器的演进解决了一些开发中的痛点,提供了更简洁、更强大的状态管理能力。
参考:
【HarmonyOS Next】鸿蒙状态管理V2装饰器详解
【HarmonyOS Next】鸿蒙状态管理装饰器V1和V2混用方案
import { Component, build, Reactive, Watch, LinkState, View } from '@ohos/hypium';// 定义一个响应式对象
class MyData { name: string = 'John'; age: number = 25;
}// 定义一个带有 @Watch 装饰器的响应式数据类
class MyReactiveData { value: number = 0;('value')onValueChange(newValue: number, oldValue: number) {console.log(`Value changed from ${oldValue} to ${newValue}`);}
}// 子组件,使用 @LinkState 进行双向数据绑定
struct Child { parentValue: number;build() {Column({ space: 20 }) {Text(`Value from parent: ${this.parentValue}`)Button('Increment Value').onClick(() => {this.parentValue++;})}}
}// 主组件,整合所有功能
struct MainComponent {private myData = new MyData();private reactiveData = new MyReactiveData(); myValue: number = 0;build() {Column({ space: 50 }) {// @Reactive 示例Column({ space: 20 }) {Text(`Name: ${this.myData.name}, Age: ${this.myData.age}`)Button('Update Data').onClick(() => {this.myData.name = 'Jane';this.myData.age = 30;})}// @Watch 示例Column({ space: 20 }) {Text(`Value: ${this.reactiveData.value}`)Button('Increment Value').onClick(() => {this.reactiveData.value++;})}// @LinkState 示例Column({ space: 20 }) {Text(`Parent value: ${this.myValue}`)Child({ parentValue: this.myValue })}}}
}
5. MVVM是什么?
MVVM(Model - View - ViewModel)是一种前端开发的软件设计模式,它是在 MVC(Model - View - Controller)和 MVP(Model - View - Presenter)模式的基础上发展而来,主要用于分离视图(UI)和业务逻辑,提高代码的可维护性、可测试性和可扩展性。
MVVM模式,应用的UI以及基础表示和业务逻辑被分成三个独立的类:视图,用于封装UI和UI逻辑;视图模型,用于封装表示逻辑和状态;以及模型,用于封装应用的业务逻辑和数据。
6. 自定义组件如何实现?
自定义组件可以将特定的 UI 元素和逻辑封装起来,提高代码的复用性和可维护性。
import { Component, build, Prop, Event } from '@ohos/hypium';
struct MyCustomComponent {// 接收父组件传递的属性 title: string = '默认标题';// 定义自定义事件 onCustomClick: () => void;build() {Column({ space: 20 }) {Text(this.title).fontSize(20).fontWeight(FontWeight.Bold)Button('点击触发自定义事件').onClick(() => {// 触发自定义事件this.onCustomClick();})}.width('100%').padding({ top: 20, bottom: 20, left: 10, right: 10 }).backgroundColor('#F0F0F0')}
}export default MyCustomComponent;
7. 纯逻辑类中如何显示弹框?
两种思路,1.由于纯逻辑类没有直接操作 UI 的能力,需要通过回调机制与 UI 组件进行交互,让 UI 组件来负责弹框的显示 2.使用解耦UI的方案进行实现,例如官方提供的OpenCustomDialog或者subWindow等。
举例第一种方案,定义回调接口:在纯逻辑类中定义一个回调接口,用于通知 UI 组件显示弹框。
在纯逻辑类中触发回调:在需要显示弹框的逻辑处调用回调方法。
在 UI 组件中实现回调:在 UI 组件中实现回调接口的方法,在该方法中编写显示弹框的逻辑。
// 定义回调接口
interface ShowDialogCallback {(message: string): void;
}class LogicClass {private showDialogCallback: ShowDialogCallback | null = null;// 设置回调函数setShowDialogCallback(callback: ShowDialogCallback) {this.showDialogCallback = callback;}// 模拟业务逻辑,触发显示弹框doBusinessLogic() {// 模拟一些业务处理const message = "这是弹框要显示的消息";if (this.showDialogCallback) {this.showDialogCallback(message);}}
}export default LogicClass;
import { Component, build, AlertDialog } from '@ohos/hypium';
import LogicClass from './LogicClass.ets';
struct Index {private logic: LogicClass = new LogicClass();private showDialog: boolean = false;private dialogMessage: string = '';build() {Column({ space: 50 }) {Button('触发业务逻辑').onClick(() => {this.logic.doBusinessLogic();})}.width('100%').padding({ top: 50, bottom: 50, left: 20, right: 20 })// 显示弹框if (this.showDialog) {AlertDialog({title: '提示',message: this.dialogMessage,onOk: () => {this.showDialog = false;}})}// 设置回调函数this.logic.setShowDialogCallback((message) => {this.dialogMessage = message;this.showDialog = true;});}
}
8. HAR和HSP分别是什么?区别是什么?
纯血鸿蒙中,HAR 是静态资源共享包,用于存放图片、配置文件等不频繁变更的内容;HSP 是用于底层及应用层动态更新文件的包。二者区别在于存储内容和更新频率不同 。
9. HSP如何可以给其应用使用?
参考:【HarmonyOS Next】 鸿蒙应用useNormalizedOHMUrl详解
10. 应用切到后台后,如何保证任务继续进行?
在鸿蒙应用开发中,当应用切到后台后,系统会对应用进行一定的管控,以优化资源利用和用户体验。为保证任务在后台继续进行,可采用以下方式:
申请后台任务权限,需要配置权限ohos.permission.KEEP_BACKGROUND_RUNNING:
{"module": {"reqPermissions": [{"name": "ohos.permission.KEEP_BACKGROUND_RUNNING","reason": "应用需要在后台持续执行任务","usedScene": {"ability": ["com.example.yourapp.MainAbility"],"when": "always"}}]}
}
或者使用服务(Service)组件。
11. UIAbility和Page以及组件的生命周期函数
UIAbility 有 onCreate、onWindowStageCreate 等生命周期函数用于自身创建、窗口阶段创建等阶段。
Page 有 onPageShow、onPageHide 等函数处理页面显示与隐藏等情况,aboutToAppear等。
组件则有自身从创建到销毁过程中的如 init、build、delete 等生命周期函数来管理其状态和渲染等操作。
11. router和Navigaiton的区别是什么?
在鸿蒙开发里,Router 和 Navigation 虽都用于页面导航,但存在明显差异。Router 功能基础,侧重于简单的页面切换,支持通过 URL 跳转,页面间数据传递需手动处理,适用于页面结构和导航逻辑简单的场景,因功能轻量,在简单场景下性能开销小、导航速度快,使用时主要调用 Router.pushUrl 方法;而 Navigation 功能更丰富,支持栈管理和便捷的返回数据处理,适合复杂导航及需处理返回数据的场景,不过因管理页面栈等操作性能开销稍大。
12. 数据临时和持久存储技术方案是什么?
数据临时存储可使用内存变量,在程序运行期间保存数据,应用关闭或进程被杀时数据丢失;还能利用函数内部的局部变量实现临时存储。而数据持久存储方面,可采用 LocalStorage,它能在本地存储数据,即使应用关闭或进程被杀,数据依然保留,存储容量有限,约 5 - 10 兆;APP Storage 也是常用方案,它存储无限制,数据存于沙箱,仅卸载应用时数据才被清除;此外,还能借助数据库,如关系型数据库或轻量级的文件数据库,来高效管理和持久存储结构化数据,满足复杂数据存储和查询需求。
13. 悬浮球如何实现?
在纯血鸿蒙中实现悬浮球,可先在配置文件里声明所需权限,如窗口显示相关权限。接着创建自定义组件作为悬浮球的 UI,设置其样式,如大小、颜色、形状等。通过系统提供的窗口管理 API 创建一个悬浮窗口,将自定义的悬浮球组件添加到该窗口中。为实现悬浮球的移动功能,要监听触摸事件,根据触摸点的坐标变化更新悬浮球的位置。同时可添加点击、长按等交互事件处理逻辑,例如点击时弹出菜单、长按可进行拖动等。最后,对悬浮球的显示和隐藏进行控制,比如在特定条件下隐藏或显示悬浮球,确保在不同场景下都能合理使用。
14. 鸿蒙应用的进程和线程
参考:【HarmonyOS Next】鸿蒙应用进程和线程详解
进程是系统进行资源分配和调度的基本单位,每个鸿蒙应用至少有一个主进程,应用启动时系统会为其分配进程资源。应用可通过配置文件声明多进程,以实现不同功能模块的隔离,提高应用的稳定性和性能,比如将数据处理、网络请求等操作放在独立进程中。线程则是进程内的执行单元,一个进程可包含多个线程。主进程中有主线程负责处理 UI 渲染和用户交互,为避免阻塞主线程导致界面卡顿,耗时操作如网络请求、文件读写等需放在子线程中执行,可使用鸿蒙提供的线程池、异步任务框架等实现多线程编程,合理利用线程能充分发挥设备多核性能,提升应用响应速度和整体性能。
15. 鸿蒙应用如何实现子线程?
参考:【HarmonyOS Next】鸿蒙TaskPool和Worker详解 (一)
16. worker和taskPool的区别
任务池(taskpool):任务池为应用程序提供一个多线程的运行环境。它主要用于处理耗时的计算任务或其他密集型任务,可以有效地避免这些任务阻塞主线程。这样不仅能最大化系统的利用率,还能降低整体资源的消耗并提高系统的整体性能。
Promise是一种用于处理异步操作的对象。它代表了一个最终可能完成(或失败)的操作及其结果值的对象。与任务池不同,Promise主要用于处理异步操作,而不是多线程计算任务。
17. webview如何和原生双向通信?
runJavaScript:异步执行JavaScript脚本,并通过回调方式返回脚本执行的结果。
onConfirm:网页调用confirm()告警时触发此回调。
或在h5注册map与回调,通过调用注册的回调方法向ArkTS侧传递数据
18.forEach与LazyforEach 还有repeat的使用与区别?
参考:
【HarmonyOS Next】鸿蒙循环渲染ForEach,LazyForEach,Repeat使用心得体会
19.折叠屏如何适配,方案有哪些?
布局适配方面,可采用响应式布局,利用弹性容器、百分比和媒体查询等技术,使界面元素能依据屏幕尺寸与比例自动调整大小和位置;采用多窗口布局,针对不同折叠状态提供不同的布局方案,如单屏、分屏等模式。资源适配时,需准备多套不同分辨率和尺寸的图片、图标等资源,以便系统根据屏幕情况加载合适的资源。交互适配要考虑不同折叠形态下用户的操作习惯变化,例如在大屏模式下支持多任务操作、手势操作等;同时,为避免因屏幕折叠引发数据丢失或异常,需做好状态保存与恢复,在屏幕折叠前后保存和恢复应用的关键数据、界面状态等。此外,还可进行性能优化,合理分配资源,避免在折叠屏设备上出现性能瓶颈。
Navigaiton分栏,全屏自适应➕布局宽高监听➕子窗口变化监听
栅栏布局➕设备媒体查询。
20.鸿蒙如何打包插件和应用?
打包应用时,首先要确保项目代码开发完成且无错误,在 DevEco Studio 里,通过配置 config.json 文件明确应用的基本信息、权限需求等;接着,选择合适的构建方式,可使用 Studio 自带的构建工具,按提示完成签名配置,包括选择签名类型、创建或导入密钥等;最后执行构建任务,系统会生成 .hap(HarmonyOS Ability Package)或 .app 格式的应用安装包。而打包插件,若为 HSP(HarmonyOS Service Package)插件,同样先完善代码开发,在 config.json 里对插件进行详细配置,明确插件类型、入口文件等信息;之后进行编译操作,完成签名后即可生成 .hsp 格式的插件包。无论打包应用还是插件,都要确保配置准确、签名合规,以保证能正常安装和使用。