//需要实现的五个基本操作(本代码带头结点)
/*
建立线性链表
线性链表元素的插入
线性链表元素的删除
访问线性链表
线性链表的读取
*/
#include<stdio.h>
#include<stdlib.h>
#include<Windows.h>
typedef int ElemType;
typedef int Status;
typedef struct LNode
{
ElemType data;
struct LNode *next;
}LNode,*LinkList;
//初始化链表,传入头结点和节点个数;
//这个方法所得到的链表是一个逆位序的,所以输入的时候就逆位输入,负负得正
Status CreateLinkList(LinkList &L, int n) {
L = (LinkList)malloc(sizeof(LNode));
if (!L) { printf("L链表的创建出现问题!\n"); return ERROR; }
L->next = NULL;
LinkList p;
printf("请输入%d个数:\n", n);
for (int i = 1; i <= n; i++) {
p = (LinkList)malloc(sizeof(LNode));
if (!p) { printf("p的初始化出现问题!\n"); return ERROR; }
scanf_s("%d", &p->data);
p->next = L->next;
L->next = p;
//头插法p->next = L->next; L->next = p;
}
return TRUE;
}
//回收链表(free每个节点都需要回收,头结点不用回收)
Status DestoryLinkList(LinkList &L) {
if (!L->next) { printf("链表的值本来就是空的!\n"); return ERROR; }
LinkList q,p;
q = L->next;
while (q) {
p = q->next;
free(q);
q = p;
}
return TRUE;
}
//顺序输出这个链表
Status GetLinkList(LinkList &L) {
if (!L->next) { printf("链表没有节点,不能输出!\n"); return ERROR; }
LinkList p;
int Tag = 1;
p = L->next;
while (p) {
printf("节点%d值是%d\n", Tag, p->data);
p = p->next;
Tag++;
}
return TRUE;
}
//在指定位置插入一个节点,第i个位置,节点值,链表;
Status InsertLinkList(LinkList &L, int i, ElemType data) {
//判断i值是否合法,i<1||i>表长---(注意方法是!p||j>i如果这两种不可能的情况发生,则i值不合法)
//j>i用来判断i<1,!p用来判断p是NULL.而且是两者有一个成立就返回
//注意判断摆放的位置,在循环找i值对应的元素之后
LinkList p;
int j = 0;
p = L;
//寻找第i-1个节点
while (p&&j < i - 1) {
p = p->next;
j++;
}
if (!p || j >= i) {
printf("传入插入函数的i值不合法\n");
return ERROR;
}
LinkList q;
q = (LinkList)malloc(sizeof(LNode));
q->data = data;
q->next = p->next;
p->next = q;
return TRUE;
}
//删除一个元素,需要确定这个元素的位置,第i个位置,返回被删除的值,链表;
Status DeleteLinkList(LinkList &L, int i, ElemType &e) {
LinkList p;
int j = 0;
p = L;
//p指向第i-1个节点,要删除第i个节点
while (p->next&&j < i-1) {//注意当删除第i个数大于表长,不能由j<i来结束循环,需要用p->next来结束,避免无效循环
p = p->next;
j++;
}
if (!p->next || j >= i) {//既然循环是以p->next结束就应该根据p->next来判断
printf("传入删除函数的i值不合法\n");
return ERROR;
}
LinkList q;
q = p->next;
e = q->data;
p->next = p->next->next;
free(q);
return TRUE;
}
//输出第i值对应的数据
Status GetElem_L(LinkList L, int i, ElemType &e) {
LinkList p;
int j = 0;
p = L;
while (p&&j < i - 1) {
p = p->next;
j++;
}
if (!p || j >= i) {
printf("得到第%d节点的值时,i的值出现问题!\n",i);
return ERROR;
}
e = p->next->data;
return TRUE;
}
int main() {
LinkList L;
int n=0;
int i1=0;
int i2=0;
int i3=0;
ElemType data=0,e2=0,e3=0;
printf("输入要初始化的链表的节点的数量!\n");
scanf_s("%d", &n);
CreateLinkList(L, n);
//输出初始化的链表
GetLinkList(L);
printf("输入要插入元素的位置!\n");
scanf_s("%d", &i1);
printf("输入要在第i个元素插入的值!\n");
scanf_s("%d", &data);
InsertLinkList(L, i1, data);
//输出增加元素后的链表
GetLinkList(L);
printf("输入要删除元素的位置!\n");
scanf_s("%d", &i2);
DeleteLinkList(L, i2, e2);
//输出删除元素后的链表
GetLinkList(L);
//输出被删除的值
printf("输出被删除的值%d\n",e2);
printf("输入要查找元素的位置!\n");
scanf_s("%d", &i3);
GetElem_L(L, i3, e3);
printf("输出被查找元素的值%d\n",e3);
DestoryLinkList(L);
system("pause");
return 0;
}