来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/climbing-stairs/
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
- 五遍刷题第一遍–1226–用时2h
- 五遍刷题第二遍–
题目描述
反转一个单链表。
示例:
输入: 1->2->3->4->5->NULL
输出: 5->4->3->2->1->NULL
方法
//https://leetcode-cn.com/problems/reverse-linked-list/solution/fan-zhuan-lian-biao-tou-cha-fa-di-gui-by-heng-29/
//https://leetcode-cn.com/problems/reverse-linked-list/solution/206-fan-zhuan-lian-biao-by-alexer-660/
//https://leetcode-cn.com/problems/reverse-linked-list/solution/dong-hua-yan-shi-206-fan-zhuan-lian-biao-by-user74/
1.头插法/迭代法
时间复杂度:O(n)
空间复杂度:O(1)
相邻三个节点 pre–>cur–> tmp(或next),以三个为一组,反转pre与cur之间的指向,然后pre和cur往后移一个节点,即tmp变成了cur。
2.递归法
时间复杂度:O(n)。
空间复杂度:O(n),由于使用递归,将会使用隐式栈空间。递归深度可能会达到 n 层。
https://leetcode-cn.com/problems/reverse-linked-list/solution/fan-zhuan-lian-biao-tou-cha-fa-di-gui-by-heng-29/
理解递归方法主要有三点:
1.先把后半部分反转递归函数更好写。如果先把前半部分反转(n1 ← n2,n3 → n4),链表就被分成了两段,想继续反转需要传 2 个参数,即第一段链表的尾(n2)和第二段链表的头(n3);而如果先把后半部分反转(n1 → n2 → n3 ← n4),仍然是一条链,n2->next->next = n3->next = n2 ,只需要一个参数,遍历到的结点(n2),即可完成反转。
2.递归过程中,n1 → n2 → n3 ←→ n4,已经反转的链是首尾相连的,成环了。要想解除环,需要让成功反转的链表尾部指向 nullptr,即 n3->next = nullptr。
3.head == nullptr 是为了特判空链表的情况。
可参考如下链接的动画演示:
https://leetcode-cn.com/problems/reverse-linked-list/solution/dong-hua-yan-shi-206-fan-zhuan-lian-biao-by-user74/
C++知识点
1.指针函数
ListNode* reverseList(ListNode* head) {}
指针函数:返回指针的函数,一个函数,它的返回值是指针;
2.递归过程不太理解
ListNode* HEAD = reverseList(head->next);
代码难点
代码
- 迭代法
class Solution {
public:
ListNode* reverseList(ListNode* head) {
if (!head) {
return nullptr;
}
ListNode* pre = head, * cur = head->next;
pre->next = nullptr;
while (cur) {
ListNode *next = cur->next;
cur->next = pre;
pre = cur;
cur = next;
}
return pre;
}
};
- 递归法
class Solution {
public:
ListNode* reverseList(ListNode* head) {
// 0 node || at the end of list
if (head == nullptr || head->next == nullptr) {//递归终止条件是当前为空,或者下一个节点为空
return head;
}
ListNode* HEAD = reverseList(head->next);//这里的HEAD就是最后一个节点
//这里请配合动画演示理解
//如果链表是 1->2->3->4->5,那么此时的cur就是5
//而head是4,head的下一个是5,下下一个是空
//所以head.next.next 就是5->4
head->next->next = head;
//防止链表循环,需要将head.next设置为空
head->next = NULL;
//每层递归函数都返回HEAD,也就是最后一个节点
return HEAD;
}
};