链表
概念:链表是一种物理结构上非连续,非顺序的存储结构,数据元素的逻辑顺序是通过链表中的指针链接次序实现的。
创建一个结点
typedef int SListDataType;
typedef struct SListNode
{
SListDataType data;
struct SListNode* next;
}SListNode;
遍历打印链表
//遍历打印链表
void SListPrint(SListNode* phead)
{
SListNode* cur = phead;
while (cur != NULL)
{
printf("%d->", cur->data);
cur = cur->next;
}
printf("NULL\n");
}
创建一个新结点
//创建一个新结点
SListNode* BuySListNode(SListDataType x)
{
SListNode* newnode = (SListNode*)malloc(sizeof(SListNode));
if (newnode == NULL)
{
printf("申请空间失败");
exit(1);
}
newnode->data = x;
newnode->next = NULL;
return newnode;
}
尾插
//尾插
void SListPushBack(SListNode** pphead, SListDataType x)
{
struct SListNode* newnode = BuySListNode(x);
if (*pphead == NULL)
{
*pphead = newnode;
}
else
{
SListNode* tail = *pphead;
while (tail->next != NULL)
{
tail = tail->next;
}
tail->next = newnode;
}
}
尾删
//尾删
void SListPopBack(SListNode** pphead)
{
//没有节点
//有一个结点
//大于一个结点
if (*pphead==NULL)
{
return;
}
else if((*pphead)->next == NULL)
{
free(*pphead);
*pphead = NULL;
}
else
{
SListNode* tail = *pphead;
SListNode* prev=NULL;
while (tail->next != NULL)
{
prev = tail;
tail = tail->next;
}
free(tail);
prev->next = NULL;
}
}
首插
//首插
void SListPushFront(SListNode** pphead, SListDataType x)
{
struct SListNode* newnode = BuySListNode(x);
newnode->next = *pphead;
*pphead = newnode;
}
首删
//首删
void SListPopFront(SListNode** pphead)
{
SListNode* tail = *pphead;
if (tail == NULL)
return;
*pphead = tail->next;
free(tail);
}
查找数据的地址
//查找
SListNode* SListFind(SListNode* phead,SListDataType x)
{
SListNode* tail=phead;
while (tail)
{
if (tail->data == x)
{
return tail;
}
else
tail = tail->next;
}
return NULL;
}
删除指定位置
//指定位置删除
void SListErase(SListNode* phead,SListNode* pos)
{
if (pos->next != NULL)
{
SListNode* posnext = pos->next;
pos->next = posnext->next;
pos->data = posnext->data;
free(posnext);
}
else
{
SListNode* prev = phead;
while (prev->next != pos)
{
prev = prev -> next;
}
free(pos);
prev->next = NULL;
}
}
SList.h
#pragma once
#include<stdio.h>
#include<stdlib.h>
#include<assert.h>
typedef int SListDataType;
typedef struct SListNode
{
SListDataType data;
struct SListNode* next;
}SListNode;
//遍历打印链表
void SListPrint(SListNode* phead);
//创建一个新的结点
SListNode* BuySListNode(SListDataType x);
//尾插
void SListPushBack(SListNode** phead, SListDataType x);
//尾删
void SListPopBack(SListNode** phead);
//头插
void SListPushFront(SListNode** pphead, SListDataType x);
//头删
void SListPopFront(SListNode** pphead);
//查找
SListNode* SListFind(SListNode* phead, SListDataType x);
//指定位置删除
void SlistErase(SListNode*phead,SListNode* pos);
SList.c
#define _CRT_SECURE_NO_WARNINGS 1
#include"SList.h"
//遍历打印链表
void SListPrint(SListNode* phead)
{
SListNode* cur = phead;
while (cur != NULL)
{
printf("%d->", cur->data);
cur = cur->next;
}
printf("NULL\n");
}
//创建一个新结点
SListNode* BuySListNode(SListDataType x)
{
SListNode* newnode = (SListNode*)malloc(sizeof(SListNode));
if (newnode == NULL)
{
printf("申请空间失败");
exit(1);
}
newnode->data = x;
newnode->next = NULL;
return newnode;
}
//尾插
void SListPushBack(SListNode** pphead, SListDataType x)
{
struct SListNode* newnode = BuySListNode(x);
if (*pphead == NULL)
{
*pphead = newnode;
}
else
{
SListNode* tail = *pphead;
while (tail->next != NULL)
{
tail = tail->next;
}
tail->next = newnode;
}
}
//尾删
void SListPopBack(SListNode** pphead)
{
//没有节点
//有一个结点
//大于一个结点
if (*pphead==NULL)
{
return;
}
else if((*pphead)->next == NULL)
{
free(*pphead);
*pphead = NULL;
}
else
{
SListNode* tail = *pphead;
SListNode* prev=NULL;
while (tail->next != NULL)
{
prev = tail;
tail = tail->next;
}
free(tail);
prev->next = NULL;
}
}
//首插
void SListPushFront(SListNode** pphead, SListDataType x)
{
struct SListNode* newnode = BuySListNode(x);
newnode->next = *pphead;
*pphead = newnode;
}
//首删
void SListPopFront(SListNode** pphead)
{
SListNode* tail = *pphead;
if (tail == NULL)
return;
*pphead = tail->next;
free(tail);
}
//查找
SListNode* SListFind(SListNode* phead,SListDataType x)
{
SListNode* tail=phead;
while (tail)
{
if (tail->data == x)
{
return tail;
}
else
tail = tail->next;
}
return NULL;
}
//指定位置删除
void SListErase(SListNode* phead,SListNode* pos)
{
if (pos->next != NULL)
{
SListNode* posnext = pos->next;
pos->next = posnext->next;
pos->data = posnext->data;
free(posnext);
}
else
{
SListNode* prev = phead;
while (prev->next != pos)
{
prev = prev -> next;
}
free(pos);
prev->next = NULL;
}
}
test.c
#define _CRT_SECURE_NO_WARNINGS 1
#include "SList.h"
int main()
{
//测试尾插
SListNode* pList=NULL;
SListPushBack(&pList, 1);
SListPushBack(&pList, 2);
SListPushBack(&pList, 3);
SListPrint(pList);
//测试头插
SListPushFront(&pList, 4);
SListPushFront(&pList, 5);
SListPushFront(&pList, 6);
SListPrint(pList);
//测试查找
SListNode* pos= SListFind(pList, 3);
printf("%p\n", pos);
SListErase(pList,pos);
SListPrint(pList);
//测试尾删
SListPopBack(&pList);
SListPopBack(&pList);
SListPopBack(&pList);
SListPopBack(&pList);
SListPrint(pList);
//测试头删
SListPopFront(&pList);
SListPopFront(&pList);
SListPopFront(&pList);
SListPopFront(&pList);
SListPrint(pList);
}
链表其实就是针对顺序表的缺点来设计的,补足的就是顺序表的缺点