Lv_ll的探究

1 lv_ll 的作用

ll 为 linked list 的简写,即链表。LittlevGL 所创建的此模块主要是服务于需要使用链表功能的对象,如 group、obj、anim、chart 等。

2 效果

lv_ll 最形象的效果体现的 lv_group 上,在前面也探究过,群对象可以使用特定功能的两个按钮来实现“上一个”、“下一个”的切换,使用到了双链表中的“前驱、“后继”,具体效果体现这里不再赘述。

3 实现过程

在 lv_ll.h 中,先是定义了结点结构体的大小为1Byte,再是定义了链表的结构体,其中包含了头结点和尾结点。

下面是初始化双链表的函数,需要提供一个指针用于初始化,并设置结点的大小(单位为字节),同时还判断了设置的大小是否是4的倍数,不是的话匹配一个4为倍数大小的空间。

再就是为链表初始化一个头结点的函数,同时返回这个头结点的指针

下图这个函数的作用是在某个结点的前面插入一个新结点

1
2
3
4
node_set_next(ll_p, n_prev, n_new);//表示将上一个结点的后继设置为这个新结点
node_set_prev(ll_p, n_new, n_prev);//表示将新结点的前驱设置为上一个结点
node_set_prev(ll_p, n_act, n_new);//表示将下一个结点的前驱设置为新插入的结点
node_set_next(ll_p, n_new, n_act);//表示将新结点的后继设置为下一个结点

这样一来新结点就插入了双链表中了

而下面这个比较简单,就是在双链表的末尾添加新节点,在前面探讨群对象的时候也使用过

当然有了插入、添加结点,自然少不了删除结点,函数的开头则是将要删除的结点中的各种参数清空,再就是把要删除的结点的前后两个结点连接起来

1
2
3
4
lv_ll_node_t* n_prev =  lv_ll_get_prev(ll_p, node_p);//表示获取要删除的结点的前驱A
lv_ll_node_t* n_next = lv_ll_get_next(ll_p, node_p);//表示获取要删除的结点的后继B
node_set_next(ll_p, n_prev, n_next);//表示将A的后继设置为B
node_set_prev(ll_p, n_next, n_prev);//表示将B的前驱设置为A

下面这个函数的作用是释放掉这个双链表的所有结点,但是这个链表仍然存在,只是为空

文章作者: Sirius65535
文章链接: http://sirius.ink/2018/05/14/lv_ll的探究/
版权声明: 本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 Sirius' Notes