c语言链表节点,数据结构。请问创建链表和节点是不是只要增加一个节点就要使用一下malloc函数和创建一个指针?

C语言数据链表
一、动态内存分配
C语言提供了一些内存管理函数,这些内存管理函数可以按需要动态分配内存空间,也可把不再使用的空间回收待用。这一部分空间分配在堆区,一般使用特定的函数进行分配。
&&&&1、常用的内存管理函数有以下三个:
&&&&1)malloc
调用形式:(类型说明符 * )malloc(size)
&&&&&&&&功能:在内存的动态分配存储区中分配一块长度为“size”字节的连续区域,用来存放类型说明符指定的类型。
&&&&&&&&返回值:分配成功则返回分配空间的起始地址,错误则返回NULL。
&&&&&例如:pc=(char
*)malloc (100);
&&&&2)calloc
&&&&&&&&调用形式:(类型说明符
*)calloc (n,size)
&&&&&&&&功能:在内存动态存储区中分配n块长度为“size”字节的连续区域。
&&&&&&&&返回值:该区域的首地址。
&&&&&&&&例如:ps=(struct
stu *)calloc (2,sizeof (struct stu));
&&&&&&&&calloc和malloc的区别仅仅在与一次可以分配n块区域。
&&&&3)释放内存空间函数free
&&&&&&&&调用形式:free(void
&&&&&&&&功能:释放ptr所指向的一块内存空间,ptr是一个任意类型的指针变量,它指向被释放区域的首地址
&&&&注意:malloc和free使用时一定要配对是使用,尽量在同一层上是使用。malloc分配的内存一定要初始化,free后的指针不允许再使用。
&&&&链表是一种常见的重要的数据结构,是将动态存储分配组织取来的一种结构。
&&&&链表的构成:链表通过在每个结构体变量中设置指向下一个变量的指针域,并存入下一个变量的地址,实现将一组结构体变量链成一条链表。链表中的每个结构体变量称为该链表的一个节点,每个节点的单元一般都没有名字,它们是通过动态分配函数生成的。
&&&&第0个节点为头结点,它存放有第一个节点的首地址,它没有数据,只是一个指针变量。以下的每个节点都分为两个域,一个是数据域,存放各种实际的数据,另一个域为指针域,存放下一节点的首地址。链表中的每个节点都是同一种结构类型。
struct student
&&&&struct
&&&&链表作为一个线性存储结构,链表的使用比数组灵活的多,构造一个链表时不一定在程序中指定链表长度,可以在程序的运行过程中动态的生成一个链表。而且链表使用完后还可以通过函数free释放掉整个链表空间。
三、链表的常用操作
&&&&链表的主要基本操作有一下几种:
&&&&1、建立链表
&&&&2、遍历输出
&&&&3、结构的查找与输出
&&&&4、插入一个节点
&&&&5、删除一个节点
&&&&&建立链表:1)申请一个新节点作为头结点。2)申请第二个节点,并且用pb指向他。3)将新申请的节点连至头结点。4)调整pf指向新申请的节点。5)将新申请的节点当作尾节点。
&&&&遍历输出:首先得到链表第一个节点的地址,即head的值。然后设一个指针变量p,先指向第一个节点,输出p所指的节点,然后使p后移一个节点,再输出,直到链表的尾节点。
&&&&查找:查找思路类似遍历输出,只是将输出换成比较,在查找到所要找的一个或全部项后结束子函数。
&&&&删除:有两种情况,一是被删除节点是第一个节点,只需是head指向第二个节点即可,即head=head-&next
二是被删除节点不是第一个节点,那么就先使被删除节点的前一个节点指向被删节点的后一节点即可,即
pf-&next=pb-&next
&&&&插入:插入分四种情况,一、原表是空表,只需使head指向被插节点即可。二、在第一个节点之前插入,使head指向被插节点,被插节点的指针域指向原来的第一节点即可。三、在其他位置插入,是插入位置的前一节点的指针域指向被插节点,使被插节点的指针域指向插入位置的后一个节点。四、在表末插入,使原表节点指针域指向被插节点,被插节点指针域置为NULL。
//=============================================================
// 语法格式:&create_head(int n)
// 实现功能:&从头到尾,正序创建一个具有n个节点的链表,并对其值进行初始化
// 参数:&&n: 链表的长度,即节点的个数
// 返回值:&&所创建链表的首地址
//=============================================================
TYPE * create_head(int n)
&struct stu *head=NULL,*pf=NULL,*pb=NULL;
&for(i=0;i&n;i++)
&&pb=(TYPE *)malloc(LEN);
&&printf("input Number and
&&scanf("%d%d",&pb-&num,&pb-&age);
&&if(i==0)
&&&pf=head=&&&//create
the first node
&&&pf-&next=&&//create
the after node
&&pb-&next=NULL;
&return(head);
//=============================================================
// 语法格式:&create_end(int n)
// 实现功能:&从尾到头,倒序创建一个具有n个节点的链表,并对其值进行初始化
// 参数:&&n: 链表的长度,即节点的个数
// 返回值:&&所创建链表的首地址
//=============================================================
TYPE * create_end(int n)
&struct stu *head=NULL,*pb=NULL;
&for(i=0;i&n;i++)
&&pb=(TYPE *)malloc(LEN);
&&printf("input Number and
&&scanf("%d%d",&pb-&num,&pb-&age);
&&if(i==0)
&&&pb-&next=NULL;&&&//create
the last node
&&&pb-&next=&&&//create
the before node
&return(head);
//=============================================================
// 语法格式:&delete(TYPE * head,int num)
// 实现功能:&删除给定序号所指向的节点
// 参数:&&*head:待删除链表
//&&&&num:
所需删除的节点
// 返回值:&&删除指定节点后的新链表首址
//=============================================================
TYPE * delete_link(TYPE * head,int num)
&TYPE *pf,*
&if(head==NULL)
&&printf("\nempty
list!\n");
&&return NULL;
&while (pb-&num!=num
pb-&next!=NULL)
&&pf=&&&&&//search
the node to be delete
&if(pb-&num==num)
&&if(pb==head)
&&&head=pb-&&&//delete
the first node
&&&pf-&next=pb-&&//delete
the other& node
&&free(pb);&&&&//free
the deleted node
&&printf("The node is
deleted\n");
&& printf("The node not been
found!\n");
//=============================================================
// 语法格式:&insert(TYPE * head,TYPE * pi)
// 实现功能:&将新申请的节点加入到指定链表中
// 参数:&&*head:待插入链表
pi:带插入节点
// 返回值:&&插入指定节点后的新链表首址
//=============================================================
TYPE * insert(TYPE * head,TYPE * pi)
&TYPE *pb ,*
&if(head==NULL)&&&&//when
the link is empty,cteate the link
&&pi-&next=NULL;
&&while((pi-&num&pb-&num)&&(pb-&next!=NULL))
&&&pb=pb-&&&//search
the node to be inster
&if(pi-&num&=pb-&num)
&&&if(head==pb)&&//insert
the node before head&
&&&&pi-&next=
&&&else&&&&//insert
the node in middle
&&&&pf-&next=
&&&&pi-&next=
&&&pb-&next=&&//inster
the node at the last
&&&pi-&next=NULL;
已投稿到:
以上网友发言只代表其个人观点,不代表新浪网的观点或立场。博客访问: 372202
博文数量: 65
博客积分: 1265
博客等级: 中尉
技术积分: 749
注册时间:
IT168企业级官微
微信号:IT168qiye
系统架构师大会
微信号:SACC2013
分类: C/C++
# include <stdio.h>
# include <stdlib.h>
typedef struct node
//定义链表中结点的结构
&int code;
&struct node *next;
}NODE,*LinkList;
/*错误信息输出函数*/
void Error(char *message)
&fprintf(stderr,"Error:%s/n",message);
//创建循环链表
LinkList createList(int n)
&LinkList head; //头结点
&LinkList p;
//当前创建的节点
&LinkList tail; //尾节点
&head=(NODE *)malloc(sizeof(NODE));//创建循环链表的头节点
&if(!head)
&&Error("memory allocation error!/n");
&head->code=1;
&head->next=head;
&tail=head;
&for(i=2;i<n;i++)
&&//创建循环链表的节点
&&p=(NODE *)malloc(sizeof(NODE));
&&tail->next=p;
&&p->code=i;
&&p->next=head;
&return head;
//创建循环链表方法2(软件设计师教程书上的方法)
LinkList createList2(int n)
&LinkList head,p;
&head=(NODE *)malloc(sizeof(NODE));
&if(!head)
&&printf("memory allocation error/n");
&&exit(1);
&head->code=1;
&head->next=head;
&for(i=n;i>1;--i)
&&p=(NODE *)malloc(sizeof(NODE));
&&&printf("memory allocation error!/n");
&&&exit(1);
&&p->code=i;
&&p->next=head->next;
&&head->next=p;
&return head;
void output(LinkList head)
&LinkList p;
&&printf("%4d",p->code);
&&p=p->next;
&while(p!=head);
&printf("/n");
void main(void)
&LinkList head;
&printf("input a number:");
&scanf("%d",&n);
&head=createList(n);
&output(head);
阅读(2896) | 评论(0) | 转发(0) |
相关热门文章
给主人留下些什么吧!~~
请登录后评论。老人有些困倦,将双脚伸进了炉堂取暖。
哪知气温骤降,海浪一波波往上冲刷着车辆。
声明:本文由入驻搜狐公众平台的作者撰写,除搜狐官方账号外,观点仅代表作者本人,不代表搜狐立场。
  如何搞定C语言链表?
  相信学了c语言的人对链表或多或少有了解,链表也是数据结构的重要内容,今天就来聊聊最简单的单向动态链表的建立与输出。首先要了解什么是链表,链表是程序设计中一种重要的动态数据结构,是动态地进行存储分配的一种结构。其中动态主要表现在元素位置可以变化,即随意删除随意插入等;元素个数可增可减,不像数组声明后长度就固定不变了。这就想起前段时间有人在群里问怎么删除素组中任意一个元素,如果没有链表刚开始学感觉就会无从下手了,这里有段代码大家可以看看:
  #include&stdio.h&
  int main()
  int a[6]={1,2,3,4,5,6};
  int n,i,j;
  printf(&输入要删除的数:&);
  scanf(&%d&,&n);
  for(i=0;i&6;i++)
  if(a[i]==n)
  for(j=i;j&6-1;j++)
  a[j]=a[j+1];
  for(i=0;i&6-1;i++)
  printf(&%d\n&,a[i]);
  return 0;
  运行结果如下:
  是使数组元素从被删除位置后面依次前移一位,然而最后一个元素依然存在,大家可以自己动手试试,这样并没有节约内存,然而链表删除就不同了。所谓动态通俗的说就是用了就开辟空间,不用就释放空间。动态存储分配的函数主要有(malloc(),calloc(),realloc(),free())大家有兴趣可以自己了解。然后就是看怎么样建立链表了,第一步我们了解链表中的元素叫节点,每个节点包含数据域和指针域这两部分。这个节点数据域可以包含很多方面的信息,这就要用到前面的结构体,数据域很容易理解,指针域就是存放下一个节点的指针即地址,这样就建立好了每个节点之间的联系。第二步来定义链表的节点,这时候我们要明白一点这个结构体的定义打破了c语言中的先定义在使用的限制,即可以用自己定义自己,这样的例子还有递归函数的定义也是这样。既然要指向下个节点的指针,那么结构体的成员必须包含指针变量,这个指针变量即可以指向其他类型的结构体数据,也可以指向自己所在的结构体类型数据。例:
  struct st
  char name[20];/*也可以写为 char *name这样可以不限长度,但编译器不同可能不能给这个分配空间,所以这里用字符数组*/
  struct st *//next是struct st类型中的一员,它又指向struct st类型数据。
  其中节点中的数据根据需要自己定义;
  第三步就是创建链表,大家肯定在想最后一个节点(尾节点)咋办呢?既然是最后一个节点肯定没有指向了,所以这里指向NULL(空指针:即不指向任何位置);有尾节点就有头节点,所以我们可以规定一个头指针head(这个指针名字可以随意定义,不是指定的),来指向链表头;定义函数struct st *creat(void)来创建链表;这里我们要定义三个struct st结构体指针变量,如下:
  Struct st *head,*p1,*p2; /*head头指针,p1指向新节点,p2指向尾节点*/
  先用动态存储非配函数malloc()为p1,p2开辟空间,p1=p2= (struct st *)malloc(sizeof(struct st));
  然后创建一个新节点,使head,p1,p2指向该节点;定义全局变量n判断是否该指向表头,此外还要设置一个节点为尾节点的标志,这里设置num==0;
  再创建二个新节点,p1指向新节点,将第二个节点放在第一个节点后面p2-&next=p1;
  使第二个节点成为表尾;然后以后依次这样走建立节点的联系,直到输入num为0时最后一个节点p2-&next=NULL;这里要主意最后一个节点的数据项即数据域是没进入链表的;
  最后就是定义void print(struct st *head)函数输出:先找到头指针然后格式输出该节点数据项,定义Struct st *p;使p=然后指针后移:p=p-&这里怎么判断是否输出结束,这就样用到循环判断了,这里我选择这样main()函数中调用以上两个函数程序就执行了,简单的链表创建,输出就结束了。下面是代码:
  #include&stdio.h&
  #include&stdlib.h&
  struct st
  char name[20];
  struct st *
  struct st *creat(void)
  struct st *head,*p1,*p2;
  p1=p2=(struct st *)malloc(sizeof(struct st));
  scanf(&%d%s%f&,&p1-&num,p1-&name,&p1-&score);
  head=NULL;
  while(p1-&num!=0)
  n=n+1;
  if(n==1)head=p1;
  else (p2-&next)=p1;
  p2=p1;
  p1=(struct st *)malloc(sizeof(struct st));
  scanf(&%d%s%f&,&p1-&num,p1-&name,&p1-&score);
  (p2-&next)=NULL;
  void print(struct st *head)
  struct st *p;
  if(head!=NULL)
  printf(&%d\t%s\t%f\n&,p-&num,p-&name,p-&score);
  }while(p!=NULL);
  void main()
  struct st *
  head=creat();
  print(head);
  运行结果如下:
  关于C语言作用域的两个例子 第一个例子:#include &stdio.h& int a=0; // 全局变量 void foo(void); int main(void) { int a=2; // main函数内的局部变量 int b=3; // main函数内的局部变量 printf(&1. main_b = %d\n&, b); printf(&main_a = %d\n&, a); foo(); printf(&2. main_b = %d\n&, b); } void foo(void){ int b=4; // foo函数内的局部变量 printf(&foo_a = %d\n&, a); printf(&foo_b = %d\n&, b); }
  输出结果:
  1. main_b = 3
  main_a = 2
  foo_a = 0
  foo_b = 4
  2. main_b = 3
  第二个例子:
  #include &stdio.h& int x = 2; int y = 3; int z = 4; void moo(int x, int *y){ x = x+3; *y = *y+3; z = z+3; /** * 这里的 z 是局部变量。 * 注意:z 没有被手动初始化。 * 不过从后面的输出结果可以看出,z 被编译器自动初始化为 0。 * 一般情况下,编译器会有一个警告,告诉你 z 没有被初始化 **/ printf(&moo : x = %1d, *y = %1d, y = %1d, z = %1d\n&, x,*y,y,z); } int main(void){ moo(x, &y); printf(&main: x = %1d1, y = %1d, z = %1d\n&, x,y,z); }
  输出结果:
  moo : x = 5, *y = 6, y = , z = 3
  main: x = 21, y = 6, z = 4
如果对编程感兴趣,想了解更多的编程知识,解决编程问题,以及入门指导,帮你解决编程中遇到的困惑,我们这里有java高手,C++/C高 手,windows/Linux高手,android/ios高手,请大家关注微信公众号:编程语言
希望对大家能够有所帮助,谢谢转载
C/C++学习群:
进入阅读原文和小编一起学习
关注微信公众号领取更多更好玩的游戏代码
欢迎举报抄袭、转载、暴力色情及含有欺诈和虚假信息的不良文章。
请先登录再操作
请先登录再操作
微信扫一扫分享至朋友圈
搜狐公众平台官方账号
生活时尚&搭配博主 /生活时尚自媒体 /时尚类书籍作者
搜狐网教育频道官方账号
全球最大华文占星网站-专业研究星座命理及测算服务机构
主演:黄晓明/陈乔恩/乔任梁/谢君豪/吕佳容/戚迹
主演:陈晓/陈妍希/张馨予/杨明娜/毛晓彤/孙耀琦
主演:陈键锋/李依晓/张迪/郑亦桐/张明明/何彦霓
主演:尚格?云顿/乔?弗拉尼甘/Bianca Bree
主演:艾斯?库珀/ 查宁?塔图姆/ 乔纳?希尔
baby14岁写真曝光
李冰冰向成龙撒娇争宠
李湘遭闺蜜曝光旧爱
美女模特教老板走秀
曝搬砖男神奇葩择偶观
柳岩被迫成赚钱工具
大屁小P虐心恋
匆匆那年大结局
乔杉遭粉丝骚扰
男闺蜜的尴尬初夜
客服热线:86-10-
客服邮箱:

我要回帖

更多关于 c语言链表的头节点 的文章

 

随机推荐