【鸿蒙生态共建】一文讲清耗时操作对定时器的超时事件影响及解决方案-《精通HarmonyOS NEXT :鸿蒙App开发入门与项目化实战》读者福利

定时器是研发过程中常用的 API,用于实现不希望代码立即运行,而是等待一段时间后再执行。例如在游戏开发中,可以使用定时器来控制游戏角色的动画播放速度和行动间隔;在数据同步场景中,可利用定时器定期检查并同步本地数据与服务器数据;在界面更新场景中,通过定时器定时刷新界面上的动态信息,如倒计时显示等。

但是,有一种情况下,会block定时器的调度,那就是在同一个函数中,启动了定时器后,在同一个线程执行了一个比较耗时的任务,这时该定时器还没有开始进行调度,会产生block,导致定时的操作没有按预期执行。

本篇内容是《精通HarmonyOS NEXT :鸿蒙App开发入门与项目化实战》这本书第9章内容的延续,是咱这本书读者的福利,在本篇内容中介绍定时器的基本写法及如书写不被block的定时器,欢迎大家一同来深入的了解,甚至可以当作面试题来学习。

对本书感兴趣的同学可以点击以下链接进行购买,或者了解我的班级参加 班级共同学习,点击链接可进入(华为官方活动)

​​​​

《精通HarmonyOS NEXT :鸿蒙App开发入门与项目化实战》读者福利博文目录,点击查看

1.定时器的基本写法

下面的示例实现了基本的定时器的写法,100毫秒后执行

复制代码
console.log("俩毛豆 测试定时器 start time");
setTimeout(()=>{
  console.log("俩毛豆 测试定时器 time out");
},100)
console.log("俩毛豆 测试定时器 调用完成");

上面的代码,执行日志如下图所示,可以看出,定时器调用完成的日志先输出,之后约100毫秒定时器时间到。

​2.增加长时任务

下面的示例在同一函数且同一线程内,调用定时器之后,增加一耗时1秒的任务。

复制代码
function longRunningFun() {
  console.log("俩毛豆 测试定时器 模拟耗时1秒开始");
  const startTime = new Date().getTime();
  while (new Date().getTime() - startTime < 1000) {
    // 空循环,模拟1秒耗时
  }
  console.log("俩毛豆 测试定时器 模拟耗时1秒结束");
}

console.log("俩毛豆 测试定时器 start time");
setTimeout(()=>{
  console.log("俩毛豆 测试定时器 time out");
},100)
longRunningFun();
console.log("俩毛豆 测试定时器 调用完成");

可以看出,耗时1秒的操作,影响了定时器的执行。

3.耗时操作使用异步的方式执行

下面的示例,将耗时的操作,使用异步的方式执行

复制代码
function longRunningFun() {
  console.log("俩毛豆 测试定时器 模拟耗时1秒开始");
  const startTime = new Date().getTime();
  while (new Date().getTime() - startTime < 1000) {
    // 空循环,模拟1秒耗时
  }
  console.log("俩毛豆 测试定时器 模拟耗时1秒结束");
}


async function  dolongRunningFunTask(): Promise<string> {
  return new Promise(resolve => {
    longRunningFun();
    resolve("")
  })
}

console.log("俩毛豆 测试定时器 start time");
setTimeout(()=>{
  console.log("俩毛豆 测试定时器 time out");
},100)
dolongRunningFunTask().then(()=>{
  console.log("俩毛豆 测试定时器 耗时任务执行完成 调用方收到事件");
});
console.log("俩毛豆 测试定时器 调用完成");

执行代码log如下图所示,可以看出,因为使用异步执行了耗时操作,定时器的超时时间,会在耗时操作之后(因为在同一个线程,且先被执行),但会在耗时操作执行完成后,立即执行(耗时操作1秒,定时器100毫秒)。

4.解决耗时操作对定时器的影响

从上面的示例代码可以看出,同一线程内的耗时操作会影响定时器的超时事件产生的时间的。如需要解决该问题,需要使用多线程的方式来执行耗时任务。

复制代码
@Concurrent
function longRunningFunConcurrent() {
  console.log("俩毛豆 测试定时器 Concurrent 模拟耗时1秒开始");
  const startTime = new Date().getTime();
  while (new Date().getTime() - startTime < 1000) {
    // 空循环,模拟1秒耗时
  }
  console.log("俩毛豆 测试定时器 Concurrent 模拟耗时1秒结束");
}

async function dolongRunningFunConcurrentTask(): Promise<string> {
  return new Promise(resolve => {
    const task: taskpool.Task = new taskpool.Task(longRunningFunConcurrent);
    taskpool.execute(task).then(() => {
      resolve("")
    })
  })
}
console.log("俩毛豆 测试定时器 start time");
setTimeout(()=>{
  console.log("俩毛豆 测试定时器 time out");
},100)
dolongRunningFunConcurrentTask().then(()=>{
  console.log("俩毛豆 测试定时器 执行完成 调用方收到事件");
});
console.log("俩毛豆 测试定时器 调用完成");

执行log如下图所示,可以看出,定时器超时的事件,并没有被耗时操作影响

5.总结

本文探讨了定时器在鸿蒙应用开发中的使用注意事项。通过示例代码展示了定时器的基本写法,以及同一线程内耗时操作对定时器执行的阻塞影响。文章提出了两种解决方案:一是将耗时操作改为异步执行,二是使用多线程技术(如taskpool)来执行耗时任务。实验结果表明,多线程方式能有效避免耗时操作对定时器的影响。本文内容节选自《精通HarmonyOSNEXT:鸿蒙App开发入门与项目化实战》一书,为读者提供了实用的定时器优化技巧。

对本书感兴趣的同学可以点击以下链接进行购买,或者了解我的班级参加 班级共同学习,点击链接可进入(华为官方活动)

相关推荐
赵财猫._.2 小时前
【Flutter x 鸿蒙】第七篇:性能优化与调试技巧
flutter·性能优化·harmonyos
Oflycomm2 小时前
华为南京研究所通感一体智慧园区项目入选 WAA 优秀案例,行业数智化转型再迎新标杆
华为·wifi7·wifi7模块
2401_860319523 小时前
【精通篇】打造React Native鸿蒙跨平台开发高级复合组件库开发系列:Badge 徽标(在右上角展示徽标数字或小红点)
react native·react.js·harmonyos
HONG````3 小时前
鸿蒙异步编程深度解析:async/await 原理、使用与实战
华为·harmonyos
小白考证进阶中3 小时前
华为HCIA/HCIP/HCIE认证考试科目大全
华为·网络工程师·hcie·hcia·hcip·华为云认证·华为认证体系
马剑威(威哥爱编程)3 小时前
【鸿蒙开发案例篇】NAPI 实现 ArkTS 与 C++ 间的复杂对象传递
c++·华为·harmonyos
国服第二切图仔3 小时前
Electron for鸿蒙PC封装的步骤进度指示器组件
microsoft·electron·harmonyos·鸿蒙pc
赵财猫._.4 小时前
【Flutter x 鸿蒙】第八篇:打包发布、应用上架与运营监控
flutter·华为·harmonyos
晚霞的不甘4 小时前
[鸿蒙2025领航者闯关]: Flutter + OpenHarmony 安全开发实战:从数据加密到权限管控的全链路防护
安全·flutter·harmonyos