「这是我参与11月更文挑战的第10天,活动详情查看:2021最后一次更文挑战」
题目
206. 反转链表
给你单链表的头节点 head ,请你反转链表,并返回反转后的链表。
示例 1:
输入: head = [1,2,3,4,5]
输出: [5,4,3,2,1]
示例 2:
输入: head = [1,2]
输出: [2,1]
示例 3:
输入: head = []
输出: []
提示:
- 链表中节点的数目范围是
[0, 5000] -5000 <= Node.val <= 5000
进阶: 链表可以选用迭代或递归方式完成反转。你能否用两种方法解决这道题?
迭代
思路
- 缓存一个空节点
prev,然后对链表进行一轮遍历; - 每次循环,把当前节点截取出来,拼接到
prev的最前面; - 循环结束,返回当前
prev节点
实现
/**
* Definition for singly-linked list.
* function ListNode(val, next) {
* this.val = (val===undefined ? 0 : val)
* this.next = (next===undefined ? null : next)
* }
*/
/**
* @param {ListNode} head
* @return {ListNode}
*/
var reverseList = function(head) {
let prev = null;
while (head) {
const next = head.next;
head.next = prev;
prev = head;
head = next;
}
return prev;
};
递归
思路
- 当前节点, 如果后续还有节点, 递归, 找到下个节点, 一直找到最后一个节点;
- 从最后一个节点开始返回, 下一个节点返回完, 改变下一个节点的
next指向自己; - 拆断当前节点原本的指向;
- 递归结束,返回最后一个节点即可。
例如: 1 -> 2 -> 3
一层层下钻,递归走到3,返回它作为最后一个节点,也就是我们待会儿的结果。
然后在2这里,改变3的指向。
在2的时候 head.next指的是3; head.next.next 原本是链表末尾,指向Null, 我们要让他掉头指向当前节点, 代码如下: head.next.next = head;。
这是链表会形成闭环,因为 2 指向 3, 3又指向2。需要拆开原链表的指向 head.next = null;。
递归结束返回的时候, 每一轮改变节点的指向即可。
实现
/**
* Definition for singly-linked list.
* function ListNode(val, next) {
* this.val = (val===undefined ? 0 : val)
* this.next = (next===undefined ? null : next)
* }
*/
/**
* @param {ListNode} head
* @return {ListNode}
*/
var reverseList = function(head) {
if (!head || !head.next) {
return head;
}
let newNode = reverseList(head.next);
// 将下个节点指向转为自己
head.next.next = head;
// 拆开正向的指向,否则将形成闭环。我看着你,你看着我
head.next = null;
return newNode;
};
看懂了的小伙伴可以点个关注、咱们下道题目见。如无意外以后文章都会以这种形式,有好的建议欢迎评论区留言。