首页 > 其他分享 >定时器

定时器

时间:2024-02-27 20:56:12浏览次数:19  
标签:定时器 删除 复杂度 到期 链表 时间

定时器的概念

程序里的定时器主要实现的功能是在未来的某个时间点执行相应的逻辑

interval:间隔时间,即定时器需要在interval时间后执行
StartTimer:添加一个定时器任务
StopTimer:结束一个定时器任务
PerTickBookkeeping: 检查定时器系统中,是否有定时器实例已经到期,相当于定义了最小时间粒度。

目前常用的几种定时器结构如下:

时间轮
最小堆
链表

他们各自对于不同事件的处理的时间复杂度如下

链表的定时器实现

链表的设计上比较简单

新增

遍历链表,找到合适的位置将定时事件插入

检查

递归检查头结点,如果到了时间就执行定时事件

最小堆的实现

可以使用c++现成的multimap来实现

众所周知红黑树的插入时间复杂度是logN,而检查事件也只需要定时检查堆顶事件就可以得到定时事件
那么红黑树删除的复杂度同样为logN,和上面的不符,那么是如何实现O1的删除复杂度的呢?

  1. 延迟删除:延迟删除意味着在堆中不会立即删除到期的定时器,而是标记为无效或删除标记。
    只有当堆顶的定时器到期时间大于当前时间时,才会执行删除操作。这样可以保证删除操作的时间复杂度是 O(1)。
    定时器到期时,如果堆顶的定时器已经被标记为无效,则丢弃它并继续执行下一个到期的定时器。

  2. 惰性删除:惰性删除是指在定时器到期时,不会立即删除它,而是将其移动到堆的末尾,并更新堆的大小。
    这样一来,堆中的定时器仍然保持有序,但已经到期的定时器位于堆的末尾,可以通过减小堆的大小来删除它们。
    由于删除操作只是减小堆的大小,因此时间复杂度为 O(1)。

时间轮的实现

实现方式是数组+链表

简单时间轮:

一个齿轮,每个齿轮保存一个超时的node链表。一个齿轮表示一个时间刻度,比如钟表里面一小格代表一秒,
钟表的秒针每次跳一格。假设一个刻度代表10ms,则2^32 个格子可表示1.36年,2^16个格子可表示10.9分钟。
当要表示的时间范围较大时,空间复杂度会大幅增加。

使用场景

在任务量小的场景下:最小堆实现,可以根据堆顶设置超时时间,数组存储结构,节省内存消耗,使用最小堆可以得到比较好的效果。
而时间轮定时器,由于需要维护一个线程用来拨动指针,且需要开辟一个bucket数组,消耗内存大,使用时间轮会较为浪费资源。

在任务量大的场景下:最小堆的插入复杂度是O(lgN), 相比时间轮O(1) 会造成性能下降。更适合使用时间轮实现。

在业界,服务治理的心跳检测等功能需要维护大量的链接心跳,因此时间轮是首选。

标签:定时器,删除,复杂度,到期,链表,时间
From: https://www.cnblogs.com/liviayu/p/18038239

相关文章

  • asp.net quartz 定时器 miniapi sqlite数据库 cors
    dotnet_miniapi_quartz_ipaddress_check/Dtos.csusingSystem.ComponentModel.DataAnnotations;namespaceGameStore.Api.Dtos;publicrecordIpAddressDto(Guidid,stringip,stringname,stringdomain,......
  • 双路音频定时器2 2025版发布 dual Sounder Timer 2025 release
    价格很便宜,只要300人民币或者60美元或者60欧元就可以用一辈子。用途是可以用来指定单路或者双路的带音频提示的定时器,可以用在一些需要定时提醒或者定时工作的场合。也可以用来矫正一些音频设备的频率,提供比较准确的音频信号输出。hepriceisverycheap,itcanbeusedfor......
  • 04. 系统滴答定时器
    一、系统滴答定时器概述  SysTick,即系统滴答定时器,它包含在M3/4/7内核里面,核心是一个24位的递减计数器。当计数值减到0时,将从RELOAD寄存器中自动重装载定时初值,开始新一轮计数。只要不把它在SysTick控制及状态寄存器中的使能位清除,就永不停息。二、SysTick寄存器介......
  • 使用基本定时器使led灯闪烁
    基本定时器原理图这两个成员在基本定时器中用不到,在stm32df103中timer6和timer7是基本定时器不可少的代码TIM_IT_Config()\\定时器中断TIM_ClearFlag()\\清除计时器中断标志位BASIC_TIM_APBxClock_FUN()\\计时器开启或者中断函数voidTIM6_IRQHandler()\\定时器中端服......
  • timeBeginPeriod 高精度定时器 Sleep
    #include"timeapi.h"#pragmacomment(lib,"winmm")//DWORD__stdcallThreadTest(LPVOIDpThreadParam){CLogmLog;inti=100;timeBeginPeriod(1);//1表示1ms精度while(i--){mLog.WriteLog("%d",i);......
  • Windows高精度定时器
     自从上次封装微秒延时函数后,利用空闲时间试着封装一个微秒定时器(类似MFC定时器形式)使用起来效果还不错。 关于定时器的几点介绍:  1.设计采用了自动释放定时器节点方式(增加虚析构函数在内部做相关释放判断,即使用完不释放节点也没关系);  2.设计采用了双向链表方......
  • 基于ATMega16定时器T1产生PWM的实例
    本例讨论ATMega16中通过定时器T1产生脉冲波形(含PWM)的具体过程,利用汇编程序实现CTC方式、快速PWM模式、相位修正PWM模式和相频修正PWM模式等实例。定时器T1与定时器T0、T2不一样,它具有16位结构,除了能实现更长时间的定时外,它还具有很多附加功能,比T0、T2要复杂一些。另外,T1还有一个很......
  • 【Flink】复函数的使用,时间服务和定时器,值、列表、字典状态变量
    【Flink】复函数的使用,时间服务和定时器,值、列表、字典状态变量文章目录一FlinkDataStreamAPI1复函数2自定义输出到下游设备二处理函数1KeyedProcessFunction的使用(1)时间服务和定时器2状态变量(1)值状态变量a需求一b需求二(2)列表状态变量(3)字典状态变量一Fl......
  • asp.net 托管服务 后台任务 定时器任务
    托管服务1\1.txtthisisatestfile托管服务1\appsettings.Development.json{"Logging":{"LogLevel":{"Default":"Information","Microsoft.AspNetCore":"Warning"}}}托管服......
  • golang定时器之timer+ticker
    转载: https://juejin.cn/post/7327157426298011663 Timer是一个一次性的定时器,用于在未来的某一时刻执行一次操作。基本使用创建Timer定时器的方式有两种:NewTimer(dDuration)*Timer:该函数接受一个time.Duration类型的参数d(时间间隔),表示定时器在过期之前等待的......