单向循环链表和单向链表差不多,只需要记录头节点的位置把单向链表判断NULL的地方改为判断头节点即可
dxxhlb.h
/*===============================================
* 文件名称:dxxhlb.h
* 创 建 者:
* 创建日期:2023年08月26日
* 描 述:
================================================*/
#ifndef _DXXHLB_H
#define _DXXHLB_H
#include <stdio.h>
#include <stdlib.h>
typedef struct Linklist{
int data;
struct Linklist *next;
}List,*Plist;
Plist create_list();
int empty_list(Plist p);
int insert_head(Plist p,int data);
int insert_tail(Plist p,int data);
int insert_pos(Plist p,int pos,int data);
int delete_pos(Plist p,int pos);
int delete_data(Plist p,int data);
int search_pos(Plist p,int pos);
int search_data(Plist p,int data);
int change_pos(Plist p,int pos,int data);
int change_data(Plist p,int old_data,int new_data);
void show(Plist p);
#endif
dxxhlb.c
/*===============================================
* 文件名称:dxxhlb.c
* 创 建 者:
* 创建日期:2023年08月26日
* 描 述:
================================================*/
#include "dxxhlb.h"
Plist create_list() //创建头节点
{
Plist p = malloc(sizeof(List));
if(NULL == p)
{
perror("malloc");
return NULL;
}
p->next = p;
return p;
}
int empty_list(Plist p)
{
return p->next == p;
}
int insert_head(Plist p,int data) //头插法,在头节点后插入节点
{
if(NULL == p)
{
return -1;
}
Plist q = malloc(sizeof(List));
if(NULL == q)
{
perror("malloc");
return -2;
}
q->next = p->next;
p->next = q;
q->data = data;
return 1;
}
int insert_tail(Plist p,int data)//尾插法,在尾节点后插入节点
{
if(NULL == p)
{
return -1;
}
Plist head = p;
while(p->next != head)
{
p = p->next;
}
Plist tail = malloc(sizeof(List));
if(NULL == tail)
{
perror("malloc");
return -2;
}
tail->next = p->next;
p->next = tail;
tail->data = data;
return 1;
}
int insert_pos(Plist p,int pos,int data) //按下标位置插入,在下标位置为pos-1的位置插入下标位置为pos的节点
{
if(NULL == p)
{
return -1;
}
while(pos--)
{
p = p->next;
}
Plist new = malloc(sizeof(List));
if(NULL == new)
{
perror("malloc");
return -2;
}
new->next = p->next;
p->next = new;
new->data = data;
return 1;
}
int delete_pos(Plist p,int pos) //删除下标位置为pos的节点,将删除位置的前一个节点与后一个节点相连
{
if(empty_list(p) || NULL == p)
{
return -1;
}
while(pos--)
{
p = p->next;
}
Plist q = p->next;
int data = q->data;
p->next = q->next;
free(q);
return data;
}
int delete_data(Plist p,int data) //删除与data值相等的所有节点
{
if(empty_list(p) || NULL == p)
{
return -1;
}
Plist head = p;
while(p->next != head)
{
if(p->next->data == data)
{
Plist q = p->next;
p->next = q->next;
free(q);
}
else
p = p->next; //要加else,否则要删除的数据排列在一起时,第一个被删除后后第二个会会被跳过判断下一个
}
return 1;
}
int search_data(Plist p,int data) //查找与data值相等的数据第一次出现的下标位置
{
if(NULL == p)
{
return -1;
}
int pos = 0;
Plist head = p;
while(p->next != head)
{
if(p->next->data == data)
{
break;
}
p = p->next;
pos++;
}
return pos;
}
int search_pos(Plist p,int pos) //查找下标位置为pos的节点数据
{
if(NULL == p)
{
return -1;
}
while(pos--)
{
p = p->next;
}
return p->next->data;
}
int change_data(Plist p,int old_data,int new_data) //将与old_data相等的数据值全部改为new_data
{
if(NULL == p)
{
return -1;
}
Plist head = p;
while(p->next != head)
{
if(p->next->data == old_data)
{
p->next->data = new_data;
}
p = p->next;
}
return 1;
}
int change_pos(Plist p,int pos,int data) //将下标位置为pos的数据改为data
{
if(NULL == p)
{
return -1;
}
while(pos--)
{
p = p->next;
}
p->next->data = data;
return 1;
}
void show(Plist p)
{
if(empty_list(p) || NULL == p)
{
return;
}
Plist head = p;
while(p->next != head)
{
printf("%d ",p->next->data);
p = p->next;
}
puts("");
}
main.c
/*===============================================
* 文件名称:main.c
* 创 建 者:
* 创建日期:2023年08月26日
* 描 述:
================================================*/
#include "dxxhlb.h"
int main(int argc, char *argv[])
{
int data,old_data,new_data,pos = 0;
Plist p = create_list();
printf("从头节点的下一位开始下标位置为0,单向循环一次结束后头节点会算入下标位置但无数据\n");
printf("**********empty_list**********\n");
data = empty_list(p);
printf("空表返回1:%d\n",data);
printf("**********insert_head**********\n");
for(int i = 0;i < 5;i++)
{
scanf("%d",&data);
insert_head(p,data);
}
printf("**********show_list**********\n");
show(p);
printf("**********insert_tail**********\n");
for(int i = 0;i < 5;i++)
{
scanf("%d",&data);
insert_tail(p,data);
}
show(p);
printf("**********insert_pos**********\n");
printf("请输入要插入的下标位置及数据:\n");
scanf("%d %d",&pos,&data);
insert_pos(p,pos,data);
printf("下标位置%d已插入数据%d如下\n",pos,data);
show(p);
printf("**********delete_pos**********\n");
printf("请输入要删除的数据下标位置:\n");
scanf("%d",&pos);
data = delete_pos(p,pos);
printf("下标位置为%d的数据%d已删除\n",pos,data);
show(p);
printf("**********delete_data**********\n");
printf("请输入要删除的数据:\n");
scanf("%d",&data);
delete_data(p,data);
printf("数据%d已全部删除\n",data);
show(p);
printf("**********search_pos**********\n");
printf("请输入要查询的下标位置:\n");
scanf("%d",&pos);
data = search_pos(p,pos);
printf("此位置的数据为%d\n",data);
show(p);
printf("**********search_data**********\n");
printf("请输入要查找的数据:\n");
scanf("%d",&data);
pos = search_data(p,data);
printf("此数据第一次出现的位置下标为%d\n",pos);
printf("**********change_pos**********\n");
printf("请输入要修改数据的下标位置及修改后的数据:\n");
scanf("%d %d",&pos,&data);
change_pos(p,pos,data);
printf("修改后如下:\n");
show(p);
printf("**********change_data**********\n");
printf("请输入要修改的数据及修改后的数据:\n");
scanf("%d %d",&old_data,&new_data);
change_data(p,old_data,new_data);
printf("值为%d的数据已全部修改为%d如下:\n",old_data,new_data);
show(p);
return 0;
}
结果