要掌握链表的相关操作,必须先熟练掌握c语言中结构体指针的应用,并掌握相关操作算法原理
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
typedef int ElemType;
typedef struct Node{
ElemType data;
struct Node*next;
}Node, *LinkList;
int listlength;//链表长度
int InitList(LinkList *H){//初始化单链表
*H = (LinkList)malloc(sizeof(Node));
(*H)->next = NULL;
return 0;
}
/*创建单链表,并返回链表长度值*/
int CreatList(LinkList H){
int flag = 1;
int i,j = 0;
ElemType c = 0;
Node *a,*b;
b=H;
while (flag){
a = (Node*)malloc(sizeof(Node));//建立新节点a
scanf("%d", &a->data);
c = a->data;
j++;
if (j == 1 && c != -1){ H->next = a; }
else{
if (c != -1){//头插法建立单链表
a->next = H->next;//将a结点插入表头
H->next = a;
}
else {//输入-1,结束创建
flag = 0;
a->next=NULL;
}
}
}
return (j - 1);//返回链表长度
}
int ConvertList(LinkList H ){//将单链表进行逆序
int i, j,count;
count=CreatList(H)-1;
listlength=count+1;
Node *r, *t, *s, *q;
q=H;
if (count < 0){
printf("链表为空");
}
else{
t = H;
for (j = 0; j<=count-1; j++){
r = H;
for (i = 0; i <= count-1; i++){
r = r->next;//指向倒数第二个数
}
s = r->next;//指向表尾
s->next = t->next;
t->next = s;
r->next = NULL;
t = s;
}
}
return 0;
}
/*按值删除*/
int deleteValueList(LinkList H,ElemType deletevalue){
Node *p,*s;
int i,b;
s=H;
p=H->next;
b=listlength;
for(i=1;i<b&&listlength>1;i++){
if(p->data==deletevalue){
s->next=p->next;//找到要删除的元素,将其删除
listlength--;//链表长度-1
p=s->next;//p重新指向s->next
}
else{//未找到,指针后移
p=p->next;
s=s->next;
}
}
if(listlength==1&&p->data==deletevalue){//链表中只剩一个元素且为将要删除的元素
H=NULL;
listlength--;//链表长度-1
}
return 0;
}
/*按位置删除*/
int deletenumberList(LinkList H,int deletenumber){
Node *p;
int i;
p=H;
for(i=1;i<deletenumber;i++){
p=p->next;//指针后移到deletenumber-1的位置
}
p->next=p->next->next;//删除位置为deletenumber的元素
listlength--;//链表长度-1
return 0;
}
/*在第insertnumber个位置插入值*/
int insertList(LinkList H,int insertnumber,ElemType insertvalue){
Node *p,*s;
int i=1;
p=H;
s = (Node*)malloc(sizeof(Node));//建立头结点
s->data=insertvalue;
for(i=1;i<insertnumber;i++){
p=p->next;//指针后移到deletenumber-1的位置
}
if(i==insertnumber){
s->next=p->next;//在insertnumber位置处插入s结点
p->next=s;
listlength++;//链表长度+1
}
return 0;
}
/*重置第resertnumber个值*/
int resetList(LinkList H,int resetnumber,ElemType *resetvalue){
int i;
Node *p,*s;
p=H;
s = (Node*)malloc(sizeof(Node));//新建结点s
s->data=*resetvalue;//将resetnumber位置元素最新值赋值给s->data
for(i=1;i<resetnumber&&i<listlength;i++){//指针后移到resetnumber-1位置
p=p->next;
}
if(i==listlength){//链表尾元素重置
p->next=NULL;
p->next=s;
}
else{
p->next=p->next->next;//删除resetnumber位置的结点
s->next=p->next;//将结点s插入resetnumber位置
p->next=s;
}
return 0;
}
/*获取特定位置的值*/
int getList(LinkList H,int getnumber){
Node *p;
ElemType e=NULL;
p=H;
for(int i=1;i<=getnumber;i++){//指针后移到resetnumber位置
p=p->next;
}
e=p->data;//获取resetnumber位置元素值
printf("%d",e);
return e;//返回resetnumber位置元素值
}
/*打印链表*/
int printList(LinkList H){
Node *p;
p=H;
for(int i=1;i<=listlength;i++){
p=p->next;//指针后移
printf("%d ",p->data);
}
return 0;
}
void menue(){
printf("\t****************************************************************\t\n");
printf("\t 0-创建单链表\t\t**\t\t1-单链表长度\n");
printf("\t----------------------------------------------------------------\t\n");
printf("\t 2-按位置删除\t\t**\t\t3-按值删除\n");
printf("\t----------------------------------------------------------------\t\n");
printf("\t 4-插入元素 \t\t**\t\t5-重置元素\n");
printf("\t----------------------------------------------------------------\t\n");
printf("\t 6-获取元素值\t\t**\t\t7-打印单链表\n");
printf("\t----------------------------------------------------------------\t\n");
printf("\t 8-退出 \t\t \t\t\n");
printf("\t****************************************************************\t\n");
}
void getFunction(int number,LinkList a){
int resetnumber=0,deletenumber=0,insertnumber=0,getnumber=0,count=0;
ElemType deletevalue=NULL,resetvalue=NULL,insertvalue=NULL;
while(number>=0&&number<=8){
switch (number)
{
case 0:{
printf("\n请创建单链表,输入单链表中元素,输入-1结束:");
ConvertList(a);
printf("\n--------------------------------------------------------------------------------\n");
break;
}
case 1:{
printf("单链表长度:%d\n",listlength);
printf("\n--------------------------------------------------------------------------------\n");
break;
}
case 2:{
if(!listlength){
printf("请先创建单链表:");
ConvertList(a);
}else{
printf("请输入要删除的元素序号:");
scanf("%d",&deletenumber);
deletenumberList(a,deletenumber);
printf("\n--------------------------------------------------------------------------------\n");
}
break;
}
case 3:{
if(!listlength){
printf("请先创建单链表:");
ConvertList(a);
}else{
printf("请输入要删除的元素值:");
scanf("%d",&deletevalue);
deleteValueList(a,deletevalue);
}
printf("\n--------------------------------------------------------------------------------\n");
break;
}
case 4:{
if(!listlength){
printf("请先创建单链表:");
ConvertList(a);
}else{
printf("请输入要插入元素位置,与值:");
scanf("%d%d",&insertnumber,&insertvalue);
while(insertnumber>listlength+1){
printf("error,请重新输入要插入元素位置,与值:");
scanf("%d%d",&insertnumber,&insertvalue);
}
insertList(a,insertnumber,insertvalue);
printf("\n--------------------------------------------------------------------------------\n");
}
break;
}
case 5:{
if(!listlength){
printf("请先创建单链表:");
ConvertList(a);
}else{
printf("请输入要更改的元素序号和要重设的值:");
scanf("%d%d",&resetnumber,&resetvalue);
resetList(a,resetnumber,&resetvalue);
printf("\n--------------------------------------------------------------------------------\n");
}
break;
}
case 6:{
if(!listlength){
printf("请先创建单链表:");
ConvertList(a);
}else{
printf("请输入要获取元素位置:");
scanf("%d",&getnumber);
getList(a,getnumber);
printf("\n--------------------------------------------------------------------------------\n");
}
break;
}
case 7:{
if(!listlength){
printf("请先创建单链表:");
ConvertList(a);
}else{
printf("链表中元素:");
printList(a);
printf("\n--------------------------------------------------------------------------------\n");
}
break;}
case 8:exit(0);
}
count++;
if(count==2){//----------------------------------------------------------------------------------------
menue();
count=0;
}
printf("请输入序号0-8:");
scanf("%d",&number);
printf("\n");
}
}
int main(){
LinkList a;
int number=0;
InitList(&a);
menue();
printf("请输入序号0-8:");
scanf("%d",&number);
printf("\n");
getFunction(number,a);
return 0;
}