libevent源码学习(10):min_heap数据结构解析

目录min_heap类型定义min_heap函数构造/析构函数及初始化判断event是否在堆顶判断两个event之间超时结构体的大小关系判断堆是否为空及堆大小返回堆顶event分配堆空间堆元素的上浮堆元素的下沉堆插入元素堆删除元素弹出堆顶元素以下源码均基于libevent-2.0.21-stable。 在libevent中,使...
摘要由CSDN通过智能技术生成

目录

min_heap类型定义

min_heap函数

构造/析构函数及初始化

判断event是否在堆顶

判断两个event之间超时结构体的大小关系

判断堆是否为空及堆大小

返回堆顶event

分配堆空间

堆元素的上浮

堆元素的下沉

堆插入元素

堆删除元素

弹出堆顶元素


以下源码均基于libevent-2.0.21-stable。

       在libevent中,使用min_heap这一数据结构来管理各个event的超时,也就是小顶堆,整个堆是根据各个event的超时时间来构成的,因此堆顶肯定就对应超时时间最小的event,这样就可以按照超时顺序进行处理了。

       关于小顶堆的性质,可以先参考堆排序中有关大顶堆的描述。

min_heap类型定义

       libevent中的min_heap是一个结构体类型,定义如下:

typedef struct min_heap
{
	struct event** p; //小顶堆的首地址
	unsigned n, a; //n为event *元素个数,a是event指针链表的长度(以event *p为单位)
} min_heap_t;

       这里涉及到了3个成员变量,对于struct event ** p,这是一个二级指针,它指向一个struct  event *型的变量,而struct event *的话,就应该很熟悉了,它指向一个事件event。通过p这个二级指针也就可以实现小顶堆对应的数组了,原因在于:在C语言中,p[i]是等价于*(p+i)的,而p作为struct event的二级指针,其指向的元素类型为struct event *型,因此 p+i 实际上就是从首地址开始偏移到第i个struct event *型元素,即p+i在数值上就等于(int)p+i*sizeof(struct event *),即p+i为第i个struct event *型元素的地址,因此*(p+i)就是第i个struct event *型元素了,因此,对于struct event ** p来说,p[i]就表示第i个struct event *元素,偏移量为i*sizeof(struct event *)。这样看来struct event ** p实际上就相当于struct event *p[capacity]指针数组,之所以不使用指针数组而是使用二级指针,是因为C语言中不存在像C++中vector那样长度可变的动态容器,如果定义为数组必须指定数组大小,这是不符合要求的,因此直接使用二级指针,在需要添加元素的时候用malloc来分配一个所需大小的内存空间即可。

       而对于另外两个成员变量,我们暂且把p作为一个数组,其中每个元素都是strcut event *类型,那么n就表示这个p数组中当前的元素个数,而a则表示p数组最多能容纳的元素个数。(不得不吐槽一下这里变量的命名。。。)这就像C++中vector的size和capacity的区别,前者表示当前容器中的元素个数,后者表示当前容器最多能容纳的元素个数。

       在正式分析函数前,还需要知道的是,每个event中,都定义了一个min_heap_idx用来存储event在这个小顶堆p数组中的索引,虽然堆中的每个元素都是一个event指针,但是建堆的依据是这些event各自设置的超时结构体ev_timeout,这是定时器小顶堆实现依据。如下所示。

struct event {
	......
	union {
		......
		int min_heap_idx;  //event在堆中的索引
	} ev_timeout_pos;
    ......
	struct timeval ev_timeout;  //超时时间
    ......
};

min_heap函数

构造/析构函数及初始化

       虽然说C语言中没有构造函数和析构函数,但是min_heap也将这种思想进行了体现在了min_heap_ctor函数和min_heap_dtor函数上,从函数名上看就是constructor和destructor的简写,各自定义如下:

void min_heap_ctor(
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值