(第一章 2)通用双向链表——带上下文的回调函数
编译时用的命令:gcc -g DList.c -o DList或
?? ? ? ? ? ? ? ?gcc ? ? ?DList.c -o DList
因为是c语言程序,不是c++,所以不用g++命令(否则报错)
?
#include <stdio.h>#include <stdlib.h>//通用双向链表typedef int DListRet;//ctx: 上下文,是所有回调函数实例的公共的环境(变量)//data: 输入参数,只被当前回调函数实例所处理typedef DListRet (*DListVisitFunc)(void *ctx, void *data);#define DLIST_RET_OK 1#define DLIST_RET_STOP 2typedef struct _DListNode{struct _DListNode* prev;struct _DListNode* next;void* data;}DListNode;typedef struct _DList{DListNode *first;}DList;//"被调用函数"(命名体现了通用型的思想)DListRet dlist_foreach(DList *thiz, DListVisitFunc visit, void *ctx){DListRet ret=DLIST_RET_OK;DListNode *iter=thiz->first;while(iter!=NULL){ret=visit(ctx,iter->data);if(ret==DLIST_RET_STOP)break;iter=iter->next;}return ret;}//"回调函数",由调用者提供DListRet dlist_max(void *ctx, void *data){int *temp=ctx;if((int)data>*temp){*temp=(int)data;}return DLIST_RET_OK;}DListRet dlist_sum(void *ctx, void *data){long long* temp=ctx;*temp+=(int)data;//printf("%d",(int)data);return DLIST_RET_OK;}DListRet dlist_print(void *ctx, void *data){printf("%d\t",(int)data);return DLIST_RET_OK;}int main(){//初始化双向链表DListNode *a=(DListNode *)malloc(sizeof(DListNode));DListNode *b=(DListNode *)malloc(sizeof(DListNode));DListNode *c=(DListNode *)malloc(sizeof(DListNode));a->data=(void *)2;b->data=(void *)5;c->data=(void *)3;a->next=b;a->prev=NULL;b->next=c;b->prev=a;c->prev=b;c->next=NULL;DList *list=(DList *)malloc(sizeof(DList));list->first=a;//调用int max=-1;dlist_foreach(list, dlist_max, &max);printf("%d\n", max);long long sum=0;dlist_foreach(list, dlist_sum, &sum);printf("%ld\n", sum);dlist_foreach(list, dlist_print, NULL);return 0;}?