接下来,我们将使用C语言实现无头节点的单链表。
头文件:
#pragma once
#include <stdio.h>
#include <assert.h>
#include <stdlib.h>typedef int SLTDateType;typedef struct SListNode
{SLTDateType data;struct SListNode* next;
}SListNode;// 动态申请一个节点
SListNode* BuySListNode(SLTDateType x);
// 单链表打印
void SListPrint(SListNode* plist);
// 单链表尾插
void SListPushBack(SListNode** pplist, SLTDateType x);
// 单链表的头插
void SListPushFront(SListNode** pplist, SLTDateType x);
// 单链表的尾删
void SListPopBack(SListNode** pplist);
// 单链表头删
void SListPopFront(SListNode** pplist);
// 单链表查找
SListNode* SListFind(SListNode* plist, SLTDateType x);
// 单链表在pos位置之后插入x
// 分析思考为什么不在pos位置之前插入?
void SListInsertAfter(SListNode** pplist, SListNode** pos, SLTDateType x);
// 单链表删除pos位置之后的值
// 分析思考为什么不删除pos位置?
void SListEraseAfter(SListNode** pplist, SListNode** ppos);// 在pos的前面插入
void SLTInsert(SListNode** pphead, SListNode** ppos, SLTDateType x);
// 删除pos位置
void SLTErase(SListNode** pplist, SListNode** ppos);
void SLTDestroy(SListNode** pplist);
函数的实现:
#include "SList.h"// 动态申请一个节点
SListNode* BuySListNode(SLTDateType x)
{SListNode* ret = (SListNode*)malloc(sizeof(SListNode));if (ret == NULL){perror("malloc");exit(0);}ret->data = x;ret->next = NULL;return ret;
}// 单链表打印
void SListPrint(SListNode* plist)
{if (plist == NULL){printf("NULL\n");return;}SListNode* tmp = plist;while (tmp){printf("%d->", tmp->data);tmp = tmp->next;}printf("NULL\n");
}// 单链表尾插
void SListPushBack(SListNode** pplist, SLTDateType x)
{assert(pplist);SListNode* NewNode = BuySListNode(x);if (*pplist == NULL){*pplist = NewNode;}else{//找尾SListNode* tmp = *pplist;while (tmp->next){tmp = tmp->next;}tmp->next = NewNode;}
}// 单链表的头插
void SListPushFront(SListNode** pplist, SLTDateType x)
{assert(pplist);SListNode* NewNode = BuySListNode(x);SListNode* tmp = *pplist;*pplist = NewNode;NewNode->next = tmp;
}// 单链表的尾删
void SListPopBack(SListNode** pplist)
{assert(pplist);if (*pplist == NULL)return;SListNode* tmp = *pplist;SListNode* prev = NULL;if (tmp->next == NULL){*pplist = NULL;free(tmp);return;}//找尾while (tmp->next){prev = tmp;tmp = tmp->next;}free(tmp);(prev->next) = NULL;
}// 单链表头删
void SListPopFront(SListNode** pplist)
{assert(pplist);if (*pplist == NULL)return;SListNode* old_head = *pplist;*pplist = (*pplist)->next;free(old_head);
}// 单链表查找
SListNode* SListFind(SListNode* plist, SLTDateType x)
{if (plist == NULL)return NULL;SListNode* tmp = plist;while (tmp != NULL){if (tmp->data == x)return tmp;tmp = tmp->next; }return NULL;
}//销毁链表
void SLTDestroy(SListNode** pplist)
{assert(pplist);if (*pplist == NULL)return;int count = 1;SListNode* tmp = *pplist;while (tmp->next){tmp = tmp->next;count++;}while (count--){SListPopBack(pplist);}
}// 单链表在pos位置之后插入x
void SListInsertAfter(SListNode** pplist, SListNode** ppos, SLTDateType x)
{SListNode* NewNode = BuySListNode(x);if ((*ppos == NULL) && (*pplist = NULL)){SListPushFront(pplist, x);return;}SListNode* tmp = *pplist;SListNode* after = *pplist;while ((tmp->next) != NULL){after = tmp->next;if (tmp == *ppos){((*ppos)->next) = NewNode;NewNode->next = after;return;}tmp = tmp->next;}if (*ppos == tmp){tmp->next = NewNode;return;}perror("The pointer does not exist");
}// 单链表删除pos位置之后的值
void SListEraseAfter(SListNode** pplist, SListNode** ppos)
{if ((*ppos == NULL) && (*pplist = NULL))return;else if ((*ppos)->next == NULL)return;SListNode* tmp = *pplist;SListNode* after = *pplist;SListNode* aafter = *pplist;while ((tmp->next) != NULL){after = tmp->next;aafter = after->next;if (tmp == *ppos){free(after);after = NULL;tmp->next = aafter;return;}tmp = tmp->next;}if (*ppos == tmp)return;elseperror("The pointer does not exist");
}// 在pos的前面插入
void SLTInsert(SListNode** pplist, SListNode** ppos, SLTDateType x)
{assert(pplist);if (*pplist == *ppos){SListPushFront(pplist, x);return;}SListNode* NewNode = BuySListNode(x);SListNode* tmp = *pplist;SListNode* prev = *pplist;while (tmp->next){if (tmp == *ppos){prev->next = NewNode;NewNode->next = tmp;return;}prev = tmp;tmp = tmp->next;}perror("The pointer does not exist");
}// 删除pos位置
void SLTErase(SListNode** pplist, SListNode** ppos)
{if ((*ppos == NULL) || (*pplist == NULL)){return;}else if ((*ppos)->next == NULL){SListPopBack(pplist);return;}SListNode* tmp = *pplist;SListNode* befor = *pplist;SListNode* after = *pplist;while ((tmp->next) != NULL){after = tmp->next;if (tmp == *ppos){free(tmp);tmp = NULL;befor->next = after;return;}befor = tmp;tmp = tmp->next;}if (*ppos == tmp)return;elseperror("The pointer does not exist");
}