linux 尾队列,libevent代码阅读(2)——尾队列的学习

libevent当中大量使用了linux内置的一个数据结构——尾队列

下面是它的使用方法:

#include #include #include #include #include #include #include #include #include #include #include #include #include #include #include using namespace std;

int main()

{

/*

定义一个结构体,它只是尾队列的一个元素

它必须包含一个TAILQ_ENTRY来指向上一个和下一个元素

*/

struct tailq_entry {

int value;

// 指向上一个元素和下一个元素

TAILQ_ENTRY(tailq_entry) entries;

};

//定义队列的头部

TAILQ_HEAD(MyQueType, tailq_entry) my_tailq_head;

// 队列初始化

TAILQ_INIT(&my_tailq_head);

//定义一个结构体指针

struct tailq_entry *item;

//定义另外一个指针

struct tailq_entry *tmp_item;

int i;

//在队列里添加10个元素

for(i=0; i<10; i++)

{

//申请内存空间

item = (tailq_entry*)malloc(sizeof(tailq_entry));

if (item == NULL)

{

perror("malloc failed");

exit(-1);

}

//设置值

item->value = i;

/*

将元素加到队列尾部

参数1:指向队列头的指针

参数2:要添加的元素

参数3:结构体的变量名

*/

TAILQ_INSERT_TAIL(&my_tailq_head, item, entries);

}

//遍历队列

printf("Forward traversal: ");

TAILQ_FOREACH(item, &my_tailq_head, entries)

{

printf("%d ",item->value);

}

printf("\n");

return 0;

}

尾队列的定义

/*

* Tail queue definitions.

*/

/*

* 尾队列的定义

* TAILQ_HEAD(name, type)定义一个名字为name,元素类型为type的双向队列

* tqh_first访问第一个元素

* tqh_last指向最后一个TAILQ_ENTRY,最后一个TAILQ_ENTRY的tqe_next为空

* 最后一个TAILQ_ENTRY的tqe_prev指向前一个TAILQ_ENTRY,

* 倒数第二个TAILQ_ENTRY的tqe_next指向最后一个元素

*/

#define TAILQ_HEAD(name, type)\

struct name {\

struct type *tqh_first;/* first element */\

struct type **tqh_last;/*最后一个元素的地址*//* addr of last next element */\

}

// 尾队列头部初始化

#define TAILQ_HEAD_INITIALIZER(head)\

{ NULL, &(head).tqh_first }

/*

* TAILQ_ENTRY(type)定义了尾队列元素访问相邻元素的入口点,即每一个元素中有一个字段为

* 该结构的对象,用于访问相邻元素

*/

#define TAILQ_ENTRY(type)\

struct {\

struct type *tqe_next;/* next element */\

struct type **tqe_prev;/* address of previous next element */\

}

/*

* tail queue access methods

*/

// 尾队列头元素

#defineTAILQ_FIRST(head)((head)->tqh_first)

// 尾队列的尾

#defineTAILQ_END(head)NULL

// 下一个元素,访问下一个元素使用elemt的field域的tqe_next

#defineTAILQ_NEXT(elm, field)((elm)->field.tqe_next)

// 最后一个元素

#define TAILQ_LAST(head, headname)\

(*(((struct headname *)((head)->tqh_last))->tqh_last))

/* XXX */

// 当前元素的上一个元素

#define TAILQ_PREV(elm, headname, field)\

(*(((struct headname *)((elm)->field.tqe_prev))->tqh_last))

// 判断队列是否为空

#defineTAILQ_EMPTY(head)\

(TAILQ_FIRST(head) == TAILQ_END(head))

// 正向遍历

#define TAILQ_FOREACH(var, head, field)\

for((var) = TAILQ_FIRST(head);\

(var) != TAILQ_END(head);\

(var) = TAILQ_NEXT(var, field))

// 反向遍历

#define TAILQ_FOREACH_REVERSE(var, head, headname, field)\

for((var) = TAILQ_LAST(head, headname);\

(var) != TAILQ_END(head);\

(var) = TAILQ_PREV(var, headname, field))

/*

* Tail queue functions.

*/

// 尾队列初始化

#defineTAILQ_INIT(head) do {\

(head)->tqh_first = NULL;\

(head)->tqh_last = &(head)->tqh_first;\

} while (0)

// 在队列头插入元素

#define TAILQ_INSERT_HEAD(head, elm, field) do {\

if (((elm)->field.tqe_next = (head)->tqh_first) != NULL)\

(head)->tqh_first->field.tqe_prev =\

&(elm)->field.tqe_next;\

else\

(head)->tqh_last = &(elm)->field.tqe_next;\

(head)->tqh_first = (elm);\

(elm)->field.tqe_prev = &(head)->tqh_first;\

} while (0)

// 在队列尾插入元素

#define TAILQ_INSERT_TAIL(head, elm, field) do {\

(elm)->field.tqe_next = NULL;\

(elm)->field.tqe_prev = (head)->tqh_last;\

*(head)->tqh_last = (elm);\

(head)->tqh_last = &(elm)->field.tqe_next;\

} while (0)

// 在指定元素的后面插入元素

#define TAILQ_INSERT_AFTER(head, listelm, elm, field) do {\

if (((elm)->field.tqe_next = (listelm)->field.tqe_next) != NULL)\

(elm)->field.tqe_next->field.tqe_prev =\

&(elm)->field.tqe_next;\

else\

(head)->tqh_last = &(elm)->field.tqe_next;\

(listelm)->field.tqe_next = (elm);\

(elm)->field.tqe_prev = &(listelm)->field.tqe_next;\

} while (0)

// 在指定元素的前面插入元素

#defineTAILQ_INSERT_BEFORE(listelm, elm, field) do {\

(elm)->field.tqe_prev = (listelm)->field.tqe_prev;\

(elm)->field.tqe_next = (listelm);\

*(listelm)->field.tqe_prev = (elm);\

(listelm)->field.tqe_prev = &(elm)->field.tqe_next;\

} while (0)

// 删除一个元素

#define TAILQ_REMOVE(head, elm, field) do {\

if (((elm)->field.tqe_next) != NULL)\

(elm)->field.tqe_next->field.tqe_prev =\

(elm)->field.tqe_prev;\

else\

(head)->tqh_last = (elm)->field.tqe_prev;\

*(elm)->field.tqe_prev = (elm)->field.tqe_next;\

} while (0)

// 替换一个元素

#define TAILQ_REPLACE(head, elm, elm2, field) do {\

if (((elm2)->field.tqe_next = (elm)->field.tqe_next) != NULL)\

(elm2)->field.tqe_next->field.tqe_prev =\

&(elm2)->field.tqe_next;\

else\

(head)->tqh_last = &(elm2)->field.tqe_next;\

(elm2)->field.tqe_prev = (elm)->field.tqe_prev;\

*(elm2)->field.tqe_prev = (elm2);\

} while (0)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值