节点(结构体描述)

struct Node {int _id;char s[50];struct Node* pre;// 指向前一个节点的地址struct Node* next;// 指向下一个节点的地址
};

新建节点(开辟内存空间)

参数: 为新节点id字段赋值
返回值:新节点的地址(指针)

struct Node* node_new(int id) {struct Node* q = (struct Node*)malloc(sizeof(struct Node));memset(q, 0, sizeof(struct Node));q->_id = id;return q;
}

添加节点

如果只有一个节点,不用添加


在最后追加节点

/*
* 为链表追加节点(加在最后)
* 参数:头节点,需要追加的节点
* 返回值:无
*/
void chain_add(struct Node* qFirst, struct Node* qAdd) {// 定位到链表头struct Node* q = qFirst;// 只要后面(next)有节点,往后找;直到没有next的节点(最后一个)for(q; q->next != NULL; q=q->next ) {node_print(q);}// 此时定位在最后一个节点,下图1// 将新节点加在最后节点的后面(next)q->next = qAdd;// 下图2qAdd->pre = q;//下图3
}

图1 定位到最后的节点:

图2 最后节点的next指向新节点:

图3 新节点的preview指针指向(前)最后节点:


计算链表中节点的个数

/*
* 获取链表长度(即节点的个数)
* 参数:头节点
* 返回值:链表长度
*/
int chain_count(struct Node* qFirst) {if (qFirst == NULL) {// 头节点都没有,长度为0return 0;}int i = 0;// 遍历链表struct Node* q = qFirst;for(q; q != NULL; q=q->next) {// 顺藤摸瓜,直到最后一个节点i++;// 找到一个就+1}return i;
}

获取节点(仿数组按序号查找,从0开始)

struct Node* chain_get(struct Node* qFirst, int index) {printf("---获取index = %d的节点:", index);int i = 0;// 遍历链表struct Node* q = qFirst;for(q; q!= NULL; q=q->next,i++ ) {if (index == i) {return q;}}return NULL;
}

打印节点

void node_print(struct Node* q) {if (NULL == q) {puts("节点打印:空节点,无可打印");return;}printf("---id = %2d---", q->_id);printf("preview = %10d ", q->pre);printf("【address = %10d】 ", q);printf("next = %10d\n", q->next);
}

打印链表

void chain_print(struct Node* qFirst) {if (qFirst == NULL) {puts("没有元素可以打印");return;}puts("----------↓↓↓打印链表------------");// 遍历链表struct Node* q;for(q = qFirst; q != NULL; q=q->next ) {node_print(q);}puts("----------↑↑↑打印链表------------");
}

删除节点

自定义函数:释放空间

节点指针是要置空的,在函数中改指针的指向,需要使用二级指针

void node_free(struct Node** q) {if( *q != NULL) {printf("free %d\n",(*q)->_id);free(*q);*q = NULL;}
}

删除节点

图4 删除头结点

图5 删除中间节点

图6 删除尾节点

1.定位到尾节点,找到其前一节点(倒数第二个节点,即将来的尾节点)

2.倒数第二节点的next节点置空

3.释放掉最后的节点

/*
* 删除节点
* 参数:1.头结点 2.待删除的结点
*       因为被删除的结点需要置空,所以需要使用二级指针
* 返回值:-1 删除失败/0 删除成功
*/
int chain_remove(struct Node** qFirst, struct Node** qRemove) {struct Node* qPre = NULL;struct Node* qNext = NULL;struct Node* q = *qFirst;// 1.输入Checkif(NULL == *qRemove){puts("删无可删!");return -1;}else{printf("删除节点:id=%d\n", (*qRemove)->_id);}// 2.删除头结点,特殊对待if(*qFirst == *qRemove ) {if((*qFirst)->next == NULL){// 就一个头结点的场合node_free(qFirst);}else{qNext = q->next;node_free(qFirst);*qFirst = qNext;}return 0;}// 3.遍历链表for(q; q != NULL; q=q->next ) {if (q == *qRemove) {qPre = q->pre;qNext = q->next;if (qNext!=NULL) {qNext->pre = qPre;qPre->next= qNext;} else {// 尾节点的场合qPre->next= NULL;}node_free(qRemove);return 0;}}
}

清空链表

void chain_clear(struct Node** qFirst) {puts("\n----------Clear------------");if (qFirst == NULL) {puts("已经是空");return;}// 遍历链表//  不断删除第一个元素while(*qFirst != NULL) {chain_remove(qFirst,qFirst);}
}

转载于:https://www.cnblogs.com/tigerlion/p/11191789.html

C语言讲义——链表的实现相关推荐

  1. 链表c语言代码题库排坐标,C语言讲义——链表完整代码

    #include #include #include struct Node { int _id; char s[50]; struct Node* pre;// 指向前一个节点的地址 struct ...

  2. 用c语言实现单链表的初始化,建表,查找,求长度,插入,删除等操作,【YTU+2430+C语言习题+链表建立+插入+删除+输(5)...

    的打印.判断链表是否为空.计算链表长度.插入节点.删除节点.删除整个链表.(2) 线性表adt顺序存储实现中的创建.查找.插入和删除等基本操作及相关算法,线性表adt链式存储实现中单链表.循环链表和双 ...

  3. C语言打印链表的中间节点的算法(附完整源码)

    C语言打印链表的中间节点的算法 C语言打印链表的中间节点的算法完整源码(定义,实现,main函数测试) C语言打印链表的中间节点的算法完整源码(定义,实现,main函数测试) #include < ...

  4. C语言通过链表指针删除链表节点的算法(附完整源码)

    C语言通过链表指针删除链表节点的算法 C语言通过链表指针删除链表节点的算法完整源码(定义,实现,main函数测试) C语言通过链表指针删除链表节点的算法完整源码(定义,实现,main函数测试) #in ...

  5. C语言删除链表的算法(附完整源码)

    C语言删除链表的算法 C语言删除链表的算法完整源码(定义,实现,main函数测试) C语言删除链表的算法完整源码(定义,实现,main函数测试) #include <iostream>st ...

  6. C语言实现链表(附完整源码)

    C语言实现链表 链表 C语言实现链表完整源码 链表 链表是一种常见的基础数据结构,结构体指针在这里得到了充分的利用.链表可以动态的进行存储分配,也就是说,链表是一个功能极为强大的数组,他可以在节点中定 ...

  7. c语言在文本每一行末尾追加字符串,c语言在末尾添加 C语言 在链表尾部添加节点...

    怎么用C语言在一个文件后面添加内容 怎么用C语言在一个文件后面添加内容 使用fopen函数打开文件,用fseek函数将文件位置调整到文件末尾,然后用fwrite函数写入数据即可.下面的示例代码,向1. ...

  8. 剑指offer之C语言实现链表(两种方式)

    1 问题 用C语言实现链表 2 代码实现 #include <stdio.h> #include <stdlib.h>#define true 0 #define false ...

  9. c语言将链表写入二进制文件_通过逐级遍历将二进制树转换为单链表的C程序

    c语言将链表写入二进制文件 Problem statement: Write a C program to convert a binary tree into a single linked lis ...

最新文章

  1. Linux基础命令---diffstat
  2. 龙邱树莓派Raspberry Pi 扩展板电路及其相关实验
  3. 如何在Python中定义二维数组
  4. java 内存溢出 内存泄露_JVM——内存泄漏与内存溢出
  5. 形参与实参, 值传递与引用传递, ref参数与out参数的区别和联系?
  6. Jmeter 5.1实现图片上传接口测试
  7. hibernate mysql自定义变量_hibernate 跟 MySql in的参数变量
  8. FileUpload上传图片提示 “GDI+中发生一般性错误”
  9. AD16自定义板子大小
  10. Tech.ED 2009特别奉献:Windows 7解读
  11. 红米手机计算机软件,红米手机怎么连接电脑,手把手教你红米手机连接电脑的方法...
  12. 一直以来伴随我的一些学习习惯(part1)
  13. 深圳哪个驾校比较好?
  14. maya表情blendshape_引用 【Maya】角色表情绑定-BlendShape的使用技巧
  15. 打印26个大写字母和26个小写字母
  16. 【浅墨著作】 OpenCV3编程入门 内容简介 勘误 配套源代码下载
  17. html a href 文件下载 IE直接打开 内容乱码
  18. linux 个人云存储_您的私人云管家 联想个人云存储上手体验
  19. [原创内容] 秒变老司机--系统更新安装和集成批处理解决方案[Win7SP1x64简体中文官方镜像专用]1.0...
  20. 40亿个整数,求上中位数

热门文章

  1. Doolittle分解法(LU分解法)的Python实现
  2. 2016年8月30日 星期二 --出埃及记 Exodus 16:31
  3. 编程中无穷大的设定 很多人可能设为0x7fffffff,这个数的确是32-bit int的最大值,符号位为0,其他的都是1 但在很多情况下,0x7fffffff会出现错误,比如溢出,这样两个无穷大数相
  4. Linux命令001:find、xargs、grep查找内容
  5. matlab covm,biosig4octmat-2.88 Matlab 脑电信号转mat数据工具包, 研究的福音。 238万源代码下载- www.pudn.com...
  6. 来自菜鸡的前端权限简单实现
  7. 上海市二级分类土地利用/土地利用规划
  8. 传奇自定义技能栏技术分享-GEE
  9. 什么是多线程上下文切换?
  10. 白细胞膜囊泡包裹在金纳米粒表面|DNA纳米结构的细胞膜囊泡|靶向细胞膜的多肽药物外泌体纳米载药