IDE:VSCode
语言:C语言
#include <stdio.h>
#include <stdlib.h>
#define TRUE 1
#define FALSE 0
#define OK 1
#define ERROR 0
#define OVERFLOW -2
typedef int Elemtype;
typedef int Status;
/* 存储结构 */
typedef struct LNode{
Elemtype data;//数据域
struct LNode *next;//指针域
}LNode, *LinkList; //*LinkList 为LNode类型的指针,当我们定义LNode *p时,可以用 LinkList p 进行替换
/* 初始化链表
1.生成新结点做头结点,用头指针L指向头结点
2.头结点的指针域置空
*/
Status InitList(LinkList *L){
*L = (LinkList) malloc(sizeof(LNode));
if(!L){
exit(OVERFLOW);
}
(*L)->next = NULL;// (*L)
}
/* 销毁链表
1.创建一个新的空表
2.释放原链表的空间
3.将空表赋值给原来的链表
*/
void DestroyList(LinkList *L){
LinkList temp;
while(*L){
temp = (*L)->next;
free(*L);
*L = temp;
}
}
/* 清空链表 DestroyList() L->next */
void ClearList(LinkList L){
LinkList p = L->next;
L->next = NULL;
DestroyList(&p);
}
/* 判断是否为空 L->next */
Status isEmpty(LinkList L){
if(L->next){
return FALSE;
}
else{
return TRUE;
}
}
/* 获取长度 p=L->next*/
int GetLength(LinkList L){
int i = 0;
LinkList p = L->next;
while(p){
i++;
p = p->next;
}
return i;
}
/* 单链表在第i个位置插入
1.申请结点s,p; p从头结点遍历至第i-1个位置
2.新结点s存放元素e
3.s->next 指向p->next;
p->next 指向s;
*/
Status InsertElem(LinkList L, int i,Elemtype e){
int j = 0;
LinkList s, p = L;
while(p && j < i - 1){
j++;
p = p->next;
}
if(!p || j > i-1){// j>i-1说明位置不对
return ERROR;
}
s = (LinkList) malloc(sizeof(LNode));
s->data = e;
s->next = p->next;
p->next = s;
return OK;
}
/* 删除第i个元素
1.使用结点p,q, p指向头结点L
2.p遍历至第i-1个元素,q指向第i个元素(q=p->next)
3.p->next 指向 q->next; *e=q->data; free(q);
*/
Status DeleteElem(LinkList L, int i, Elemtype *e){
int j = 0;
LinkList q, p = L;
while(p && j < i-1){
j++;
p = p->next;
}
if(!p || j > i-1){
return ERROR;
}
q = p->next;
p->next = q->next;
*e = q->data;
free(q);
return OK;
}
/* 根据位置获取元素
1.p指针指向头结点的下一个元素
*/
Status GetElem(LinkList L, int i,Elemtype *e){
int j =1;
LinkList p=L->next;
while(p && j < i){//直到j==i
j++;
p = p->next;
}
if(!p || j > i){
return ERROR;
}
*e = p->data;
return OK;
}
/* 比较两个元素是否相等 相等为0 大于为1 小于为-1*/
Status compare(Elemtype e1,Elemtype e2){
if(e1 == e2){return 0;}
else if(e1 > e2) {return 1;}
else {return -1;}
}
/* 查找元素的指定位置 */
int FindElem(LinkList L,Elemtype e, Status (*cpmpare)(Elemtype,Elemtype)){
int i = 0;
LinkList p = L->next;
while(p){
i++;
if(!compare(p->data,e)){//相等时返回0,a>b返回1,小于返回-1
return i;
}
p = p->next;
}
return 0;
}
/* 获取前驱元素
1.指针p用于遍历,指针q指向p->next;
2.如果q->data == cur_e
前驱元素就是 p->data
*/
Status PreElem(LinkList L,Elemtype cur_e,Elemtype *pre_e){
LinkList q, p = L->next;
while(p->next){
q = p->next;
if(q->data == cur_e){
*pre_e = p->data;
return OK;
}
p = q;
}
return ERROR;
}
/* 获取后继元素 */
Status NextElem(LinkList L, Elemtype cur_e,Elemtype *next_e){
LinkList p = L->next;
while(p->next){
if(p->data == cur_e){
*next_e = p->next->data;
return OK;
}
p = p->next;
}
return ERROR;
}
/* 访问元素 */
void visit(Elemtype e){
printf("%d",e);
}
/* 遍历链表 */
Status TraverseList(LinkList L, void (*visit)(Elemtype)){
LinkList p = L->next;
while(p){
visit(p->data);
p = p->next;
}
}
int main(){
LinkList L;
InitList(&L);
Elemtype e;
int i;
if (L){
printf("init success\n");
}
if (isEmpty(L)){ // 判断链表是否为空
printf("list is empty\n");
}
for (i = 0; i < 10; i++){ // 插入元素
InsertElem(L, i + 1, i);
}
if (GetElem(L, 1, &e)) { // 获取元素的值
printf("The first element is %d\n", e);
}
printf("length is %d\n", GetLength(L)); // 获取表长
printf("The 5 at %d\n", FindElem(L, 5, *compare)); // 查找元素
PreElem(L, 6, &e); // 获取元素 6 的前驱元素
printf("The 6's previous element is %d\n", e);
NextElem(L, 6, &e); // 获取元素 6 的后继元素
printf("The 6's next element is %d\n", e);
DeleteElem(L, 1, &e); // 删除元素
printf("delete first element is %d\n", e);
printf("list:");
TraverseList(L,visit); // 遍历链表
DestroyList(&L); // 销毁线性表
if (!L) {
printf("\ndestroy success\n");
}
}
运行结果:
shiyanlou:project/ $ gcc -o 3.1 3.1.c [18:29:19]
shiyanlou:project/ $ ./3.1 [18:29:22]
init success
list is empty
The first element is 0
length is 10
The 5 at 6
The 6's previous element is 5
The 6's next element is 7
delete first element is 0
list:123456789
destroy success