位于contiki-ng-release-v4.6\os\lib下的list.h list.c这个链表库。链表是惯穿整个OS,是OS灵魂所在。
C指针发挥到了极致,链表重要性,不言而谕了,认真理解并掌握它,技能会有本质上的提升。
先看一下list.h这个文件,有个大概的认识:
#ifndef LIST_H_ #define LIST_H_ #include <stdbool.h> #define LIST_CONCAT2(s1, s2) s1##s2 #define LIST_CONCAT(s1, s2) LIST_CONCAT2(s1, s2) /** * Declare a linked list. * 声明一个链表。 */ #define LIST(name) \ static void *LIST_CONCAT(name,_list) = NULL; \ static list_t name = (list_t)&LIST_CONCAT(name,_list) /** * Declare a linked list inside a structure declaraction. * 在结构声明中声明一个链表。 */ #define LIST_STRUCT(name) \ void *LIST_CONCAT(name,_list); \ list_t name /** * Initialize a linked list that is part of a structure. * 初始化作为结构一部分的链表。 */ #define LIST_STRUCT_INIT(struct_ptr, name) \ do { \ (struct_ptr)->name = &((struct_ptr)->LIST_CONCAT(name,_list)); \ (struct_ptr)->LIST_CONCAT(name,_list) = NULL; \ list_init((struct_ptr)->name); \ } while(0) /** * The linked list type.链接列表类型。 * */ typedef void ** list_t; void list_init(list_t list); void * list_head(list_t list); void * list_tail(list_t list); void * list_pop (list_t list); void list_push(list_t list, void *item); void * list_chop(list_t list); void list_add(list_t list, void *item); void list_remove(list_t list, void *item); int list_length(list_t list); void list_copy(list_t dest, list_t src); void list_insert(list_t list, void *previtem, void *newitem); void * list_item_next(void *item); bool list_contains(list_t list, void *item); #endif /* LIST_H_ */
回顾C知识点,void ** list_t是指针的指针; void * list_head(list_t list)是指针函数,返回是地址;
void list_add(list_t list, void *item)你可认得它? void (*fun)(int)这是函数指针;
像我这样刚入门的一些新手,很容易被【函数指针】【指针函数】【数组指针】【指针数组】搞得晕头转向;
其实它们没这么复杂,唯一的法门就是,理解它们的本质,多练习它们的用法。
时间:2020-01-13
/*------------------------list链表应用----------------------------------------*/ #include "lib/list.h" //加载lib的链表库 typedef struct list_struct //新结构体名字; { struct list_struct *next; //指针 int num; //号码 }listr; PROCESS(list_process, "list process"); PROCESS_THREAD(list_process, ev, data) { LIST(_listr); //申明一个链表 static listr el1, el2;//定义结构体变量 static listr *pr;//定义一个指针 list_init(_listr); el1.num = 5; el2.num = 6; list_add(_listr,&el1); list_add(_listr,&el2); PROCESS_BEGIN(); while(1) { pr = list_head(_listr);//找到链表头 ////////////////////////////////////////// do{ printf("_listr num:%d\n",pr->num); //打印整个链表的num参数 pr = list_item_next(pr); }while(pr!=NULL); ////////////////////////////////////////// printf("list process exit!!\n\n"); PROCESS_EXIT(); //退出进程,释放资源 } PROCESS_END(); }
/*------------------------所有自启动的测试PROCESSES---------------------------*/ AUTOSTART_PROCESSES(
&list_process );
执行效果(IAR for contiki NG),看来list这是一个单链表,不是双向的。
时间:2021-1-22
由链表实现的数据结构,可以去学习contiki-ng-release-v4.6\examples\libs\data-structures下的data-structures.c,这个例子将指针和链表,
发挥到了极致,通过查看printf了解软件执行的流程。你会发现在学校所学C的难点 重点,在OS里面常常被使用,就像家常便饭一样的。
想了想,这人类的思维能力还 真是强大!!