重庆分公司,新征程启航
为企业提供网站建设、域名注册、服务器等服务
在给定的单链表的第i位上插入值为n的节点。
创新互联是由多位在大型网络公司、广告设计公司的优秀设计人员和策划人员组成的一个具有丰富经验的团队,其中包括网站策划、网页美工、网站程序员、网页设计师、平面广告设计师、网络营销人员及形象策划。承接:成都网站建设、做网站、网站改版、网页设计制作、网站建设与维护、网络推广、数据库开发,以高性价比制作企业网站、行业门户平台等全方位的服务。
#include stdio.h
#includemalloc.h
#define N 5
typedef int elemtype;
typedef struct node
{
elemtype data;
struct node *next;
}linklist;
linklist *Creatlist(linklist*L){
L=(linklist*)malloc(sizeof(linklist));
L-next=NULL;
return L;
}
int Judge(linklist *L){
if(L-next==NULL)
{
printf("建表成功...\n");
}
else
printf("建表失败.\n");
return 0;
}
int Input(linklist *L,int x,linklist *r){
int i;
linklist *p;
p=(linklist*)malloc(sizeof(linklist));
p-data=x;
p-next=NULL;
r-next=p;
printf("%d ",p-data);
return 0;
}
int Insert1(linklist *L,int i){
linklist *p,*q,*r,*t;
int j=1,item;
p=L-next;
q=L;
r=L;
if(L-next==NULL)
{
printf("表空.\n");
return 0;
}
else
{
while(p!=NULLji)
{
q=p;
p=p-next;
j++;
}
if(p==NULL)
{
printf("%d不在表的范围内.\n");
return 0;
}
else
{
t=(linklist*)malloc(sizeof(linklist));
t-next=NULL;
printf("请输入item:");
scanf("%d",item);
t-data=item;
t-next=p;
q-next=t;
}
printf("在第%d位上插入值为%d的节点后的所有数据为\n",i,item);
for(j=0;jN+1;j++)
{
r=r-next;
printf("%d ",r-data);
}
printf("\n");
return 1;
}
}
int main()
{
int i,item,k;
linklist *L,*r;
printf("单向链表的创建(包括初始化)与输出\n");
L=Creatlist(L);
Judge(L);
printf("表中的数据为:");
r=L;
Input(L,11,r);
r=r-next;
Input(L,32,r);
r=r-next;
Input(L,17,r);
r=r-next;
Input(L,46,r);
r=r-next;
Input(L,9,r);
r=r-next;
printf("\n");
printf("在给定的单链表的第i位上插入值为item的节点\n");
printf("请输入i:");
scanf("%d",i);
Insert1(L,i);
return 0;
}
在给定单链表的值为m的节点的前面插入一个值为n的节点
#include stdio.h
#includemalloc.h
#define N 5
typedef int elemtype;
typedef struct node
{
elemtype data;
struct node *next;
}linklist;
linklist *Creatlist(linklist*L){
L=(linklist*)malloc(sizeof(linklist));
L-next=NULL;
return L;
}
int Judge(linklist *L){
if(L-next==NULL)
{
printf("建表成功...\n");
}
else
printf("建表失败.\n");
return 0;
}
int Input(linklist *L,int x,linklist *r){
int i;
linklist *p;
p=(linklist*)malloc(sizeof(linklist));
p-data=x;
p-next=NULL;
r-next=p;
printf("%d ",p-data);
return 0;
}
int Insert2(linklist *L,int item){
linklist *p,*q,*r,*t;
int j=1,m;
p=L-next;
r=L;
q=L;
if(L-next==NULL)
{
printf("表空.\n");
return 0;
}
else
{
while(p!=NULL)
{
if(p-data!=item)
{
q=p;
p=p-next;
}
else
break;
}
if(p==NULL)
{
printf("%d不在表的范围内.\n");
return 0;
}
else
{
t=(linklist *)malloc(sizeof(linklist));
t-next=NULL;
printf("请输入m:");
scanf("%d",m);
t-data=m;
q-next=t;
t-next=p;
}
}
printf("在值为%d的节点的前面插入一个值为%d的节点后的所有数据为\n",item,m);
for(j=0;jN+1;j++)
{
r=r-next;
printf("%d ",r-data);
}
printf("\n");
return 1;
}
int main()
{
int i,item,k;
linklist *L,*r;
printf("单向链表的创建(包括初始化)与输出\n");
L=Creatlist(L);
Judge(L);
printf("表中的数据为:");
r=L;
Input(L,11,r);
r=r-next;
Input(L,32,r);
r=r-next;
Input(L,17,r);
r=r-next;
Input(L,46,r);
r=r-next;
Input(L,9,r);
r=r-next;
printf("\n");
printf("在给定单链表的值为item的节点的前面插入一个值为m的节点\n");
printf("请输入item:");
scanf("%d",item);
Insert2(L,item);
return 0;
}
学到指针,也要开始学习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-xhm-xh)/*当只剩下一个记录时,u=0*/
{m=a;
u=i;
}
}
*p=m;
for(i=0;iu;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;i5;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;i5;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();
}
首先,主函数中,“请输入插入的数据”那里scanf应该是b,这是引发崩溃的原因。
其次,insert函数的目的应该是想插入数据后仍是有序链表。但你的insert函数逻辑太乱,有些不必要的判断,我修正了你的代码,贴给你看看。(虽然你insert是想保证有序,但你在创建的时候没有保证有序,所以最终结果不一定是有序。例如,创建 1,5,2,插入3,最后输出的是 1,3,5,2)
代码修改:
scanf("%d", b);
重写了insert函数,简化逻辑;
动态分配的内存记得释放,增加freeNode释放空间
#include stdio.h
#include stdlib.h
struct link
{
int data;
struct link *next;
};
struct link *add(struct link *head);//创建链表
void display(struct link *head);//输出数据
struct link *insert(struct link *head, int b); //插入新节点
void freeNode(struct link *); //释放空间
int main()
{
char c;
struct link *head = NULL;
printf("要创建一个链表吗?");
scanf(" %c", c);
while (c == 'y' || c == 'Y')
{
head = add(head);
printf("要继续创建节点吗?");
scanf(" %c", c);
}
display(head);
int b;
printf("输入插入的数据");
scanf("%d", b);
head = insert(head, b);
display(head);
freeNode(head);
}
struct link *add(struct link *head)
{
int data;
struct link *p = (struct link*)malloc(sizeof(struct link));
if (head == NULL)
{
head = p;
}
else
{
struct link *pr = head;//一个临时指针pr先保存下head的地址
while (pr-next != NULL)
{
pr = pr-next;
}
pr-next = p;
}
printf("输入数据");
scanf("%d", p-data);
p-next = NULL;
return head;
}
void display(struct link *head)
{
struct link *pr = head;
while (pr != NULL)
{
printf("%d\n", pr-data);
pr = pr-next;
}
}
struct link *insert(struct link *head, int b)
{
struct link *ptr = head, *prev = head;
struct link *newNode = (struct link *)malloc(sizeof(struct link));
newNode-data = b;
while (ptr b ptr-data) {
prev = ptr;
ptr = ptr-next;
}
newNode-next = ptr;
if (ptr == head) head = newNode;
else prev-next = newNode;
return head;
}
void freeNode(struct link *node) {
if (!node) return;
freeNode(node-next);
free(node);
}
如果已知一个节点指针pre和一个节点指针cur,要把cur插入到pre节点之后,很显然要保证链表不会断开而丢失后面的节点,要先把后面的节点指针(指向lat的指针)保存下来,即有cur-next
=
pre-next,然后把cur连接的一串链表连接到pre后面,即pre-next
=
cur;
上面介绍了,在一个节点之后插入节点的情况。这是通常的情况。如果要向一个链表的头部插入节点,就只需要将新节点的下一个指针指向链表的头指针即可。
在这种情况下,有两点要注意:
1,链表是否为空链表
2,要插入的节点是不是空指针。
代码实现:
//向单链表中插入一个节点(插入在链开始处)
//输入参数:单链表的头指针和要插入的节点指针
//输出参数:无
//返回值:指向单链表的头指针
singlelist*
insert(singlelist
*head,singlelist
*node)
{
if(node
==
null)
{
return
head;
}
else
if(head
==
null)
{
return
node;
}
node-next
=
head;
head
=
node;
return
head;
}
s-data=y;
写反了。
void insert_list(list *head,int i,int y)
{
list *p,*s;int j=0;
p=head;
do
{
p=p-next;
j++;
}while(ji-1);
if(j==i-1)
{
s=(list *)malloc(sizeof(list));
/* 这里写反了 y=s-data; */
s-data=y;
s-next=p-next;
p-next=s;
}
}
1.main函数中的LinkList L;
改成
LinkList L = (LinkList)malloc(sizeof(LNode));
2.PrintfList函数中把L = (LinkList)malloc(sizeof(LNode));这一句去掉
原因是main函数中的L变量是个没初始化的野指针,L作为参数传入TailCreateList函数并不会改变L的值,这点你可以调试的时候跟踪L的值