删除链表之two star programming
最近偶尔看到一篇关于Linus Torvalds的访问,大神说大部分人都不理解指针。假设被要求写一段链表删除节点的程序,大多数的做法都是跟踪两个指针,当前指针cur和其父节点pre,这种实现很容易理解,但是并没有用到指针的精髓。
Linus是怎么写的呢,且看源代码
//链表之two star programming
#include <stdio.h> typedef struct node
{
int value;
struct node *next;
}listNode; listNode *insert(listNode *head, int value)
{
listNode *newNode = new listNode;
newNode->value = value;
newNode->next = head;
return newNode;
} void erase(listNode **head_in, int value)
{
listNode **cur = head_in;
while (*cur)
{
listNode *p = *cur;
if (p->value == value)
{
*cur = p->next;
delete p;
}
else
{
cur = &(p->next);
}
}
//return head;
} void printList(listNode *head)
{
listNode *p = head;
while(p)
{
printf("%d ", p->value);
p = p->next;
}
printf("\n");
} int main()
{
listNode *head = NULL;
int select, a;
do
{
printf("请输入选择 1--插入, 2--删除, 3--输出,其他跳出\n");
scanf("%d", &select);
if(select == 1)
{
printf("输入将要插入的值, -1表示结束\n");
while(scanf("%d", &a), a != -1)
{
head = insert(head, a);
}
}
else if(select == 2)
{
printf("输入将要删除的值, -1表示结束\n");
while(scanf("%d", &a), a != -1)
{
erase(&head, a);
}
}
else if(select == 3)
{
printList(head);
}
else break; } while (1); getchar();
return 0;
}
运行结果

在链表的删除节点函数earse()中,并不是把头结点指针head作为参数传入,而是传入指针head的引用,小雨来分析一下运行过程,直接上图说明


可以看出cur的移动比较有意思,它是沿着节点之间的指针移动的,在这里,我们也可以把指针当成一种特殊的节点。
当然现在并不提倡这种编程风格,虽然看起来很简洁,但是太晦涩,不能让人一眼看懂,Linus说一般操作系统核心部分用这种方式。
删除链表之two star programming的更多相关文章
- [LeetCode] Delete Node in a Linked List 删除链表的节点
Write a function to delete a node (except the tail) in a singly linked list, given only access to th ...
- 剑指Offer面试题:12.在O(1)时间删除链表结点
一.题目:在O(1)时间删除链表结点 题目:给定单向链表的头指针和一个结点指针,定义一个函数在O(1)时间删除该结点. 原文采用的是C/C++,这里采用C#,节点定义如下: public class ...
- 【编程题目】在 O(1)时间内删除链表结点
60.在 O(1)时间内删除链表结点(链表.算法).题目:给定链表的头指针和一个结点指针,在 O(1)时间删除该结点.链表结点的定义如下:struct ListNode{int m_nKey;List ...
- [CareerCup] 2.3 Delete Node in a Linked List 删除链表的节点
2.3 Implement an algorithm to delete a node in the middle of a singly linked list, given only access ...
- 链表:删除链表中重复的结点(java实现)
题目描述 在一个排序的链表中,存在重复的结点,请删除该链表中重复的结点,重复的结点不保留,返回链表头指针. 例如,链表1->2->3->3->4->4->5 处理后 ...
- lintcode:删除链表中指定元素
题目 删除链表中等于给定值val的所有节点. 样例 给出链表 1->2->3->3->4->5->3, 和 val = 3, 你需要返回删除3之后的链表:1-> ...
- 【面试题013】在O(1)时间删除链表结点
[面试题013]在O(1)时间删除链表结点 我们要删除结点i,我们可以把结点i的下一个结点j的内容复制到结点i,然后呢把结点i的指针指向结点j的下一个结点.然后在删除结点j. 1.如果结点i位于链表 ...
- lintcode:在O(1)时间复杂度删除链表节点
题目: 在O(1)时间复杂度删除链表节点 给定一个单链表中的表头和一个等待被删除的节点(非表头或表尾).请在在O(1)时间复杂度删除该链表节点.并在删除该节点后,返回表头. 样例 给定 1->2 ...
- lintcode:Remove Nth Node From End of Lis 删除链表中倒数第n个节点
题目: 删除链表中倒数第n个节点 给定一个链表,删除链表中倒数第n个节点,返回链表的头节点. 样例 给出链表1->2->3->4->5->null和 n = 2. 删除 ...
随机推荐
- Roslyn 的确定性构建
注意到每次编译完之后,你的 dll 或者 exe 是不一样的吗?本来这并没有什么大不了的,但大家都知道数字和鹅厂的安全软件遍布在我们大(tiān)陆(cháo)地区的大量电脑上,它们的查杀策略是——凡 ...
- Redis构建全局并发锁
Redis构建全局并发锁 https://www.cnblogs.com/FG123/p/9990336.html 谈起Redis的用途,小伙伴们都会说使用它作为缓存,目前很多公司都用Redis作为缓 ...
- sublime python运行插件
Tools->New plugin 粘贴下面代码,在插件目录新建文件夹,保存 import sublime, sublime_plugin import os class ExampleComm ...
- WPF自适应可关闭的TabControl 类似浏览器的标签页(转)
效果如图: 虽然说是自适应可关闭的TabControl,但TabControl并不需要改动,不如叫自适应可关闭的TabItem. 大体思路:建一个用户控件,继承自TabItem,里面放个按钮,点击的时 ...
- 一次解决spark history server日志不见
通过cloudera的旧版VM(centos6版本)跑spark,之后,想看一下日志研究一下job,stage以及task,压力很大的发现完全没有日志,180088页面打开后: Event log d ...
- 军哥LNMP优化
http://bbs.vpser.net/thread-8914-1-1.html http://www.zxsdw.com/index.php/archives/881/ 修改/usr/local/ ...
- 关于angular的好文推荐
独立作用域篇 1)http://www.angularjs.cn/A09C 2)http://www.cnblogs.com/wangmeijian/p/4944030.html 理解$watch , ...
- JAVASE02-Unit011: TCP通信(小程序)
TCP通信(小程序) server端: package chat; import java.io.BufferedReader; import java.io.IOException; import ...
- SQL 函数:树结构指定父节点遍历所有的子节点
CREATE function [dbo].[Get_DepChildren] ( @ID int ) , ),PID ), Name )) as begin --declare @ID Int -- ...
- [实践]使用JarJar优雅的发布依赖包
[实践]使用JarJar优雅的发布依赖包 打包工具: Jar Jar Links是一个Java类库重新打包工具. 可以帮助你将其它用到的java库打包并嵌入到你自己的项目jar包中.这样做的原因有: ...