链表-C语言实现
来源:互联网 发布:移动电玩城作弊软件 编辑:程序博客网 时间:2024/04/27 02:42
单向链表
list.h
//list.h#ifndef LIST_H#define LIST_H#include <stdlib.h>typedef struct ListElmt_{ void *data; struct ListElmt_ *next;} ListElmt;typedef struct List_{ int size; int (*match)(const void *key1, const void *key2); void (*destroy)(void *data); ListElmt *head; ListElmt *tail;} List;/* public interface */void list_init(List *list, void (*destroy)(void *data));void list_destroy(List *list);int list_ins_next(List *list, ListElmt *element, const void *data);int list_rem_next(List *list, ListElmt *element, void **data);#define list_size(list) ((list)->size)#define list_head(list) ((list)->head)#define list_tail(list) ((list)->tail)#define list_is_head(list, element) ((element) == (list)->head ? 1 : 0)#define list_is_tail(element) ((element)->next == NULL ? 1 : 0)#define list_data(element) ((element)->data)#define list_next(element) ((element)->next)#endif
list.c
//list.c#include <stdlib.h>#include <string.h>#include "list.h"/** * 初始化链表 * @param list 要初始化的链表 * @param destory 如果节点中的数据需要destroy,则提供destroy函数,该函数 * 在list_destroy中被调用,用于销毁节点中的数据。如果节点中的数据不需要销毁, * 则该参数传NULL。 */void list_init(List *list, void (*destroy)(void *data)){ list->size = 0; list->destroy = destroy; list->head = NULL; list->tail = NULL;}/** * 销毁链表 * @param list 要销毁的链表 */void list_destroy(List *list){ void *data; while (list_size(list) > 0) { if (list_rem_next(list, NULL, (void **)&data) == 0 && list->destroy != NULL) { list->destroy(data); } } memset(list, 0, sizeof(List));}/** * 将元素data插入到链表list的element节点后面。如果element为NULL, * 则新的节点插入到链表的开始。 * @param list 要操作的链表 * @param element 指定的节点 * @param data 要插入的数据 * @return 成功返回0;失败返回-1; */int list_ins_next(List *list, ListElmt *element, const void *data){ ListElmt *new_element; if ((new_element = (ListElmt *)malloc(sizeof(ListElmt))) == NULL) return -1; new_element->data = (void*)data; if (element == NULL) { /* 当链表中没有节点时 */ if (list_size(list) == 0) list->tail = new_element; new_element->next = list->head; list->head = new_element; } else { /* 当指定的元素为最后一个节点时 */ if (element->next == NULL) list->tail = new_element; new_element->next = element->next; element->next = new_element; } list->size++; return 0;}/** * 将节点element从链表list中删除 * @param list 要操作的链表 * @param element 指定的节点 * @param data 用于保存被删除的节点中的数据 * @return 成功返回0;失败返回-1; */int list_rem_next(List *list, ListElmt *element, void **data){ ListElmt *old_element; if (list_size(list) == 0) return -1; if (element == NULL) { *data = list->head->data; old_element = list->head; list->head = list->head->next; if (list_size(list) == 1) list->tail = NULL; } else { if (element->next == NULL) return -1; *data = element->next->data; old_element = element->next; element->next = element->next->next; /* 如果移除的是尾节点,调整尾节点 */ if (element->next == NULL) list->tail = element; } free(old_element); list->size--; return 0;}
双向链表
dlist.h
/** * 双向链表,dlist.h */#ifndef DLIST_H#define DLIST_H#include <stdlib.h>typedef struct DListElmt_{ void *data; struct DListElmt_ *prev; struct DListElmt_ *next;} DListElmt;typedef struct DList_{ int size; int (*match)(const void *key1, const void *key2); void (*destroy)(void *data); DListElmt *head; DListElmt *tail;} DList;/* public interface */void dlist_init(DList *list, void (*destroy)(void *data));void dlist_destroy(DList *list);int dlist_ins_next(DList *list, DListElmt *element, const void *data);int dlist_ins_prev(DList *list, DListElmt *element, const void *data);int dlist_remove(DList *list, DListElmt *element, void **data);#define dlist_size(list) ((list)->size)#define dlist_head(list) ((list)->head)#define dlist_tail(list) ((list)->tail)#define dlist_is_head(list, element) ((element) == (list)->head ? 1 : 0)#define dlist_is_tail(element) ((element)->next == NULL ? 1 : 0)#define dlist_data(element) ((element)->data)#define dlist_next(element) ((element)->next)#define dlist_prev(element) ((element)->prev)#endif
dlist.c
/** * 双向链表,dlist.c */#include <stdlib.h>#include <string.h>#include "dlist.h"/** * 初始化链表 * @param list 要初始化的链表 * @param destory 指定一个销毁数据的函数,该函数会在dlist_destroy中调用。 */void dlist_init(DList *list, void (*destroy)(void *data)){ list->size = 0; list->destroy = destroy; list->head = NULL; list->tail = NULL;}/** * 销毁链表 * @param list 要销毁的链表 */void dlist_destroy(DList *list){ void *data; while (dlist_size(list) > 0) { if (dlist_remove(list, dlist_tail(list), (void **)&data) == 0 && list->destroy != NULL) { list->destroy(data); } } memset(list, 0, sizeof(DList));}/** * 将元素插入由list指定的双向链表中element元素之后。如果element为NULL。 * 则将元素插入到链表的开始位置。新的元素包含一个指向data的指针,因此只要 * 该元素仍在链表中,data所引用的内存空间就应该保持合法。由调用者负责管理 * data所引用的存储空间。 * @param list 要操作的链表 * @param element 指定的节点 * @param data 要插入的元素 * @return 成功返回0,失败返回-1 */int dlist_ins_next(DList *list, DListElmt *element, const void *data){ DListElmt *new_element; if ((new_element = (DListElmt *)malloc(sizeof(DListElmt))) == NULL) return -1; new_element->data = (void *)data; if (element == NULL) { if (dlist_size(list) == 0) { new_element->next = NULL; new_element->prev = NULL; list->head = new_element; list->tail = new_element; } else { new_element->next = list->head; new_element->prev = NULL; list->head->prev = new_element; list->head = new_element; } } else { new_element->next = element->next; new_element->prev = element; if (element->next == NULL) list->tail = new_element; else element->next->prev = new_element; element->next = new_element; } list->size++; return 0;}/** * 将元素插入由list指定的双向链表中element元素之前。如果element为NULL。 * 则将元素插入到链表的开始位置。新的元素包含一个指向data的指针,因此只要 * 该元素仍在链表中,data所引用的内存空间就应该保持合法。由调用者负责管理 * data所引用的存储空间。 * @param list 要操作的链表 * @param element 指定的节点 * @param data 要插入的元素 * @return 成功返回0,失败返回-1 */int dlist_ins_prev(DList *list, DListElmt *element, const void *data){ DListElmt *new_element; if ((new_element = (DListElmt *)malloc(sizeof(DListElmt))) == NULL) return -1; if (element == NULL) { if (dlist_size(list) == 0) { list->head = new_element; list->tail = new_element; new_element->next = NULL; new_element->prev = NULL; } else { new_element->next = list->head; new_element->prev = NULL; list->head->prev = new_element; list->head = new_element; } } else { new_element->next = element; new_element->prev = element->prev; if (element->prev == NULL) list->head = new_element; else element->prev->next = new_element; element->prev = new_element; } return 0;}/** * 将元素element从链表中移除 * @param list 要操作的链表 * @param element 要从链表中移除的节点 * @param data 移除的节点中的数据 * @return 成功返回0;失败返回-1。 */int dlist_remove(DList *list, DListElmt *element, void **data){ if (element == NULL || dlist_size(list) == 0) return -1; *data = element->data; if (element == list->head) { list->head = element->next; if (list->head == NULL) list->tail = NULL; else element->next->prev = NULL; } else { // 将前一个节点的next指向当前节点的下一个节点 element->prev->next = element->next; // 如果这个节点是最后一个节点,删除后,将尾指针指向当前节点的前一个节点; // 如果不是最后一个节点,则将后一个节点的prev指向当前节点的前一个节点。 if (element->next == NULL) list->tail = element->prev; else element->next->prev = element->prev; } free(element); list->size--; return 0;}
单向循环链表
clist.h
/** * 单向循环链表,clist.h */#ifndef CLIST_H#define CLIST_H#include <stdlib.h>typedef struct CListElmt_{ void *data; struct CListElmt_ *next;} CListElmt;typedef struct CList_{ int size; int (*match)(const void *key1, const void *key2); void (*destroy)(void *data); CListElmt *head;} CList;/* public interface */void clist_init(CList *list, void (*destroy)(void *data));void clist_destroy(CList *list);int clist_ins_next(CList *list, CListElmt *element, const void *data);int clist_rem_next(CList *list, CListElmt *element, void **data);#define clist_size(list) ((list)->size)#define clist_head(list) ((list)->head)#define clist_data(element) ((element)->data)#define clist_next(element) ((element)->next)#endif
clist.c
/** * 单向循环链表,clist.c */#include <stdlib.h>#include <string.h>#include "clist.h"void clist_init(CList *list, void (*destroy)(void *data)){ list->size = 0; list->destroy = destroy; list->head = NULL;}void clist_destroy(CList *list){ void *data; while (clist_size(list) > 0) { if (clist_rem_next(list, list->head, (void **)&data) == 0 && list->destroy != NULL) { list->destroy(data); } } memset(list, 0, sizeof(CList));}/** * 插入元素到链表list的节点element后面。 * @param list 链表 * @param element 节点 * @param data 数据 * @return 成功返回0,失败-1 */int clist_ins_next(CList *list, CListElmt *element, const void *data){ CListElmt *new_element; if ((new_element = (CListElmt *)malloc(sizeof(CListElmt))) == NULL) return -1; new_element->data = (void *)data; if (clist_size(list) == 0) { new_element->next = new_element; list->head = new_element; } else { new_element->next = element->next; element->next = new_element; } list->size++; return 0;}/** * 从链表list中删除element节点。 * @param list 链表 * @param element 节点 * @param data 被删除节点中的数据 * @return 成功返回0,失败返回-1 */int clist_rem_next(CList *list, CListElmt *element, void **data){ CListElmt *old_element; if (clist_size(list) == 0) return -1; *data = element->next->data; if (element->next == element) { old_element = element->next; list->head = NULL; } else { old_element = element->next; element->next = element->next->next; if (old_element == clist_head(list)) list->head = old_element->next; } free(old_element); list->size--; return 0;}
0 0
- 链表c语言实现
- 链表-C语言实现
- 链表 C语言实现
- 链表C语言实现
- 链表(LinkedList) C 语言实现
- 链表ADT C语言实现
- 链表ADT C语言实现
- 链表(C语言实现)
- DataStructure---LinkList 链表C语言实现代码
- 使用C语言实现“泛型”链表
- 使用C语言实现“泛型”链表
- 使用C语言实现“泛型”链表
- 链表、栈、队列的C语言实现
- C语言实现头插法(链表)
- 栈的C语言实现(链表)
- 链栈 C语言实现
- 地球 c语言实现
- C语言实现堆栈
- HTML5简介及HTML5的发展前景
- Genymotion下载慢的解决办法
- Java线程池使用说明
- Android编程权威指南(第二版)学习笔记(二十三)—— 第23章 HTTP 与后台任务
- 由坐标数据生成点SHP文件,并由多组点生成线SHP文件(下)
- 链表-C语言实现
- scala基础语法-1变量、类型、循环、方法、函数
- Cordova环境搭建
- C++中堆和栈的解析
- 用异或来交换两个变量是错误的
- Python中Counter计数统计
- 函数极大值
- C语言volatile关键字详解
- 深度理解微信小程序的思想