C语言 单链表的插入删除操作

两个单链表linklist1,linklist2。linklist1中结点包括学生的学号和下一个结点的指针,linklist2中结点包括linklist1链表每个学号对应的学生成绩。
把两个单链表合并成单链表conlink,结点包括学号,对应的成绩和下一个结点的指针,单链表按学号升序排列。
我的程序如下
#include "stdio.h"
struct linklist1
{int xh;
struct linklist1 *next;
};
struct linklist2
{int grade;
struct linklist2 *next;
};
struct conlink
{int xh;
int grade;
struct conlink *next;
};

struct linklist1 *creat1()
/**创建单链表a**/
{int i;
struct linklist1 *head,*p,*q;
head=(struct linklist1 *)malloc(sizeof(struct linklist1));
p=q=head;
for(i=0;i<5;i++)
{p=(struct linklist1 *)malloc(sizeof(struct linklist1));
scanf("%d",&(p->xh));
q->next=p;
q=p;
}
p->next=0;
return head;
}

struct linklist2 *creat2()
\**创建单链表b**\
{int i;
struct linklist2 *head,*p,*q;
head=(struct linklist2 *)malloc(sizeof(struct linklist2));
p=q=head;
for(i=0;i<5;i++)
{p=(struct linklist2 *)malloc(sizeof(struct linklist2));
scanf("%d",&(p->grade));
q->next=p;
q=p;
}
p->next=0;
return head;
}

scan(struct linklist1 *a,struct linklist2 *b,struct linklist1 **p,struct linklist2
**q)
\**查找单链表中学号最大的结点,存入*p,对应的成绩存入*q**\
{struct linklist1 *m;
int i=0,u=0;
m=a->next;
while(a->next!=0)
{a=a->next;
i++;
if(a->xh>m->xh)
{m=a;
u=i;
}
}
*p=m;
for(i=0;i<u;i++)
b=b->next;
*q=b;
}

conlink(struct conlink *head,struct linklist1 **p,struct linklist2 **q)
\**用头插法建立单链表c**\
{struct conlink *a;
a=(struct conlink *)malloc(sizeof(struct conlink));
a->xh=(*p)->xh;
a->grade=(*q)->grade;
a->next=head->next;
head->next=a;
}

outlist1(struct linklist1 *head,struct linklist1 **p)
/**删除a单链表中学号最大的结点(最大的结点用scan函数已经找出)**/
{while(head->next!=(*p))
head=head->next;
head->next=(*p)->next;
}

outlist2(struct linklist2 *head,struct linklist2 **q)
/**删除b单链表中对应的结点**/
{while(head->next!=(*q))
head=head->next;
head->next=(*q)->next;
}

output(struct conlink *head)
/**输出c链表**/
{
while(head->next!=0)
{printf("%d %d\n",head->next->xh,head->next->grade);
head=head->next;
}
}

main()
{struct linklist1 *a;
struct linklist2 *b;
struct linklist1 *p;
struct linklist2 *q;
struct conlink *head;
a=creat1();
b=creat2();
head=(struct conlink *)malloc(sizeof(struct conlink));
head->next=0;
while(a->next!=0)
{scan(a,b,&p,&q);
conlink(head,&p,&q);
outlist1(a,&p);
outlist2(b,&q);
}
output(head);
}我的程序总是在删除linklist1链表中结点时陷入死循环,请高手分析原因。

第1个回答  2009-03-02
学到指针,也要开始学习C语言的调试技能了,发现问题,最好自己调试解决。

如果编程软件支持断点,单步调试等功能那就最好了,如果不支持,也可以使用printf()语句打印相关的变量值来进行调试。

主要问题出在scan()函数
scan(struct linklist1 *a,struct linklist2 *b,struct linklist1 **p,struct linklist2 **q)
{
struct linklist1 *m;
int i=0,u=0;
m=a->next;
while(a->next!=0)
{a=a->next;
i++;
if(a->xh>m->xh)/*当只剩下一个记录时,u=0*/
{m=a;
u=i;
}
}
*p=m;
for(i=0;i<u;i++) /* u=0时,这个循环不会执行 */
b=b->next;
*q=b; /* u=0时,这里就出错了 */
}

修改后的代码,有简单的调试信息输出
#include "stdio.h"
struct linklist1
{
int xh;
struct linklist1 *next;
};
struct linklist2
{
int grade;
struct linklist2 *next;
};

struct conlink
{
int xh;
int grade;
struct conlink *next;
};

struct linklist1 *creat1()
/**创建单链表a**/
{
int i;
struct linklist1 *head,*p,*q;
head=(struct linklist1 *)malloc(sizeof(struct linklist1));
p=q=head;
printf("please input 5 xh:\n");
for(i=0;i<5;i++)
{p=(struct linklist1 *)malloc(sizeof(struct linklist1));
scanf("%d",&(p->xh));
p->next=0;
q->next=p;
q=p;
}
return head;
}

struct linklist2 *creat2()
/**创建单链表b**/
{int i;
struct linklist2 *head,*p,*q;
head=(struct linklist2 *)malloc(sizeof(struct linklist2));
p=q=head;
printf("please input 5 grade:\n");
for(i=0;i<5;i++)
{p=(struct linklist2 *)malloc(sizeof(struct linklist2));
scanf("%d",&(p->grade));
p->next=0;
q->next=p;
q=p;
}
return head;
}

scann(struct linklist1 *a,struct linklist2 *b,struct linklist1 **p,struct linklist2
**q)
/**查找单链表中学号最大的结点,存入*p,对应的成绩存入*q**/
{
struct linklist1 *m = a->next;
printf("scan()...\n");
while(a->next && b->next)
{
a=a->next;
b=b->next;
if(a->xh >= m->xh)
{
*p=a;
*q=b;
printf("xh=%d grade = %d\n", (*p)->xh, (*q)->grade);
getch();
}
}
}

conlink(struct conlink *head,struct linklist1 *p,struct linklist2 *q)
/**用头插法建立单链表c**/
{
struct conlink *a;
printf("conlink()...\n");
a=(struct conlink *)malloc(sizeof(struct conlink));
a->xh=p->xh;
a->grade=q->grade;
a->next=head->next;
head->next=a;
}

outlist1(struct linklist1 *head,struct linklist1 *p)
/**删除a单链表中学号最大的结点(最大的结点用scan函数已经找出)**/
{
while(head->next && head->next!=p)
head=head->next;
head->next=p->next;
free(p);
}

outlist2(struct linklist2 *head,struct linklist2 *q)
/**删除b单链表中对应的结点**/
{
while(head->next && head->next!=q)
head=head->next;
head->next=q->next;
free(q);
}

output(struct conlink *head)
/**输出c链表**/
{
while(head->next!=0)
{
printf("%d %d\n",head->next->xh,head->next->grade);
head=head->next;
}
}

main()
{
struct linklist1 *a;
struct linklist2 *b;
struct linklist1 *p;
struct linklist2 *q;
struct conlink *head;
a=creat1();
b=creat2();
head=(struct conlink *)malloc(sizeof(struct conlink));
head->next=0;
while(a->next!=0)
{
scan(a,b,&p,&q);
conlink(head,p,q);
outlist1(a,p);
outlist2(b,q);
}
output(head);
getch();
}本回答被提问者采纳
第2个回答  2009-03-02
while(a->next!=0)
a->next!=NULL
地址值肯定不会使用0这个地址……
p->next=0中,改成NULL

outlist1(struct linklist1 *head,struct linklist1 **p)
/**删除a单链表中学号最大的结点(最大的结点用scan函数已经找出)**/
{while(head->next!=(*p))
head=head->next;
head->next=(*p)->next;
}
最好加上一句 free (*p);比较好
第3个回答  2009-03-02
(问题1)struct linklist1 *creat1()
/**创建单链表a**/
{int i;
struct linklist1 *head,*p,*q;
p=q=(struct linklist1 *)malloc(sizeof(struct linklist1));
head=NULL;
for(i=0;i<5;i++)
{scanf("%d",&(p->xh));
if(i==0)head=p;
else q->next=p;
q=p;
p=(struct linklist1 *)malloc(sizeof(struct linklist1));
}
q->next=NULL; //结束标示
return head;
}
(问题2)注释应该时“/”,不是“\”;
(问题3)#include <stdlib.h>/*这个头文件时包含malloc函数和free函数*/
(问题4)有必要些那么多函数吗?不是一个linklist1对应一个linklist2,这样的话可以直接连接两个链表
完整代码:

#include <stdlib.h>
#include <stdio.h>

struct linklist1
{int xh;
struct linklist1 *next;
};
struct linklist2
{int grade;
struct linklist2 *next;
};
struct conlink
{int xh;
int grade;
struct conlink *next;
};

struct linklist1 *creat1()
/**创建单链表a**/
{int i;
struct linklist1 *head,*p,*q;
p=q=(struct linklist1 *)malloc(sizeof(struct linklist1));
head=NULL;
for(i=0;i<5;i++)
{
printf("%d ",i);
scanf("%d",&(p->xh));
if(i==0)head=p;
else q->next=p;
q=p;
p=(struct linklist1 *)malloc(sizeof(struct linklist1));
}
q->next=NULL;
return head;
free(p);free(q);free(head);
}
struct linklist2 *creat2()
/**创建单链表b**/
{int i;
struct linklist2 *head,*p,*q;
p=q=(struct linklist2 *)malloc(sizeof(struct linklist2));
head=NULL;
for(i=0;i<5;i++)
{printf("%d ",i);
scanf("%d",&(p->grade));
if(i==0)head=p;
else q->next=p;
q=p;
p=(struct linklist2 *)malloc(sizeof(struct linklist2));
}
q->next=NULL;
return head;
free(p);free(q);free(head);
}

struct conlink *link(struct linklist1 *a,struct linklist2 *b)
/**连接两个单链表**/
{
struct conlink *p,*q,*head;
int n=0;
head=NULL;
p=q=(struct conlink *)malloc(sizeof(struct conlink));

while (a!=NULL&&b!=NULL)
{
p->xh=a->xh;
p->grade=b->grade;
n++;
if (n==1) head=p;
else q->next=p;
q=p;
p=(struct conlink *)malloc(sizeof(struct conlink));
a=a->next;b=b->next;
}
q->next=NULL;
return head;
}

output(struct conlink *head)
/**输出c链表**/
{ struct conlink *p;
p=head;
if (head!=NULL)
{

do
{
printf("%d %d\n",p->xh,p->grade);

p=p->next;
} while(p!=NULL);
}
}

main()
{struct linklist1 *a;
struct linklist2 *b;

struct conlink *head;
a=creat1();
printf("\n\n\n");
b=creat2();

head=(struct conlink *)malloc(sizeof(struct conlink));
head=NULL;
head=link(a,b);
output(head);
free(a);free(b);free(head);
}
第4个回答  2009-03-02
删除linklist1链表,没有必要那么麻烦啊 ,直接赋值为NULL就可以了

用c语言实现单链表以及单链表的建立、清空、插入、删除、查找、修改等...
程序如下:include <string.h>#include <stdio.h>#include <stdlib.h>struct st{long num; char name[20]; float score; struct st *next;};\/* 创建结点 *\/struct st *creat(){struct st *head=NULL,*p,*q;q=p=(struct st *)malloc(sizeof(struct st));scanf("%ld%s%f",&p->num...

用c语言调用实现带头结点的单链表的建立,插入,删除,查找的源代码
直接插入。小于的话,移动有序表后插入 int j= i-1; int x = a[i]; \/\/复制为哨兵,即存储待排序元素 a[i] = a[i-1]; \/\/先后移一个元素 while(x < a[j]){ \/\/查找在有序表的插入位置 a[j+1] = a[j]; j--; \/\/元素后移 } ...

用C语言头插法或尾插法建立带头结点的单链表,实现单链表上的插入,删除...
\/* 初始条件:顺序线性表L已存在,1≤i≤ListLength(L) *\/ \/* 操作结果:用e返回L中第i个数据元素的值 *\/ Status GetElem(LinkList L,int i,ElemType *e){ int j;LinkList p; \/* 声明一结点p *\/ p = L->next; \/* 让p指向链表L的第一个结点 *\/ j = 1; \/* j为计数...

c语言 链表操作:建立,显示及节点的插入,删除
LNode *next;};typedef LNode *LinkList; \/\/ 另一种定义LinkList的方法 \/\/单链表线性表的基本操作(12个)int InitList(LinkList &L){ \/\/ 操作结果:构造一个空的线性表L L=(LinkList)malloc(sizeof(LNode)); \/\/ 产生头结点,并使L指向此头结点 if(!L) \/\/ 存储分配失败 exit(0);L-...

数据结构代码(用C语言) 单链表的插入和删除
\/\/链表建立 Node* creat(){ Node *head = NULL, *p = NULL, *s = NULL;int Date = 0, cycle = 1;head = (Node*)malloc(sizeof(Node));if(NULL == head){ printf("分配内存失败\\r\\n");return NULL;} head->pstnext = NULL;p = head;while(cycle){ printf("请输入数据且当...

C语言编程——单链表的建立与维护,要求:由主函数调用单链表的建立、元素...
scanf("%d",&top->n);top->next=NULL;p0=top;while(--n){ p=(link*)malloc(sizeof(link));printf("输入数据 ");scanf("%d",&p->n);p0->next=p;p->next=NULL;p0=p;} return top;} void inlink(int n,link *p0,link *p) \/\/插入 p q之间 { link *r;r=(link*)m...

实现单链表的建立、清空、插入、删除查找、修改等运算。用数据结构...
void insert_list(LNode *,int,int );\/\/插入一个元素 int delete_list(LNode *,int);\/\/删除一个元素 \/\/创建一个空链表 LNode *creat_head(){ LNode *p;p=(Llist)malloc(sizeof(LNode));p->next=NULL;return(p);} \/\/创建一个长度为n的线性链表 void creat_list(LNode *head,int...

用C语言编写链式存储结构下实现线性表的创建,插入,删除,按值查找
j++;} return p;} \/*单链表的按值查找*\/ LinkList LocalElem(LinkList la,int e){ LNode* p=la->next;while(p!=NULL && p->data!=e)p=p->next;return p;} \/*单链表插入操作*\/ bool InsertList(LinkList la,int i,int e){ \/\/在la链表中的i位置插入数值e int j=1;...

C语言编程:26个英文字母建立单链表,可插入删除查找和求长度
voie Insert(PLNode head,int position,char chr)\/*插入到第i的位置*\/ {int i;PNLode p,q;if(Length(head)+1<position){printf("你要插入的位置不存在!");exit(0);} else {p=head;i=0;while(i<position-1){p=p->next;i++;} q=(PLNode)malloc(sizeof(LNode));q->character=...

...的录取查找删除添加等功能。用链表实现插入删除功能。
\/\/利用单链表编写一个学生成绩系统。(具有查询成绩、修改成绩、删除成绩、添加成绩、全班平均等功能。)include<stdio.h> include<stdlib.h> include<string.h> define MAXSIZE 100 typedef char nametype;typedef float gradetype;typedef struct node{ nametype name[MAXSIZE];gradetype grade;struct...

相似回答