先注声明:解题思路:借鉴、归纳及总结 意在记录学习过程(非原创)
但文字部分及所用图片均来自个人 谢绝转载
1.链表基本操作之虚拟头结点
联想:数据处理的基本操作:增删改查
基于链表这一数据结构,头结点和非头结点的操作往往不同,需要一点分类讨论
但虚拟头结点的引入可以实现将(实际)头结点和非头结点统一起来
典例1:LeetCode203 移除链表元素 力扣
小结:移除元素或者添加元素都是很基本的操作,每一步都有理有据。
比起直接处理原链表,引用虚拟头结点能使问题简单化。
2.链表基本操作之插入删除 LeetCode707 707. 设计链表 - 力扣(Leetcode)
备注:难度不大,但需要注意细节,要求常练常熟。(代码略)
3.反转链表 LeetCode206 206. 反转链表 - 力扣(Leetcode)
解法一:双指针法:
解法二:递归法:
备注:用迭代法或递归法求解问题都是殊途同归,只是无非有几点需要思考并注意:
1.初始条件 2.终止条件 3.循环内的一次完整操作(需要为下一次做准备)
1.初始条件:pre = NULL, cur = head [ 与反转末态对应]
但temp作为临时储存cur->next 的变量,却不能在定义时直接赋值。
因为不能确定cur是否为空指针,即cur->next不一定操作有效。
2.终止条件是pre ==NULL 还是cur ==NULL?
一旦末态条件不甚清楚,最好的办法就是画出末态图进行分析。
3.循环内的一次操作:反转链表关系+ pre/ cur指针的后移
联想:复杂的问题往往可以拆解为若干个子问题。
若子问题具有大致相同的特性,则递归是非常好的处理手段。
想到递归,或许能想到“多诺米骨牌”。子问题间看似独立,实则蕴含关联。
递归函数入口传递初始化的条件,每一次递归类比一次赋值操作后的再循环。
if - else 的大框架下,if 写明终止条件及返回量,else下注清每一次循环间的操作。
或许,如何把握循环不变量,找到子问题间的牵连关系,始终会是一个核心难题。