题目描述
给你单链表的头节点 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
思路
头插法:
原链表可以视为是通过尾插法进行插入的,如果一开始是用头插法插入的话,就相当于把原链表翻转过来了。
双指针法:
首先定义一个cur指针,指向头结点,再定义一个pre指针,初始化为null。然后开始反转,首先要把 cur->next 节点用tmp指针保存一下,接下来要改变 cur->next 的指向,将cur->next 指向pre ,此时已经反转了第一个节点了。接下来,就是循环了,继续移动pre和cur指针。最后,cur 指针已经指向了null,循环结束,链表也反转完毕了。 此时我们return pre指针就可以了,pre指针就指向了新的头结点。
代码
C++版:
方法一:
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* ListNode *next;
* ListNode() : val(0), next(nullptr) {}
* ListNode(int x) : val(x), next(nullptr) {}
* ListNode(int x, ListNode *next) : val(x), next(next) {}
* };
*/
class Solution {
public:
ListNode* reverseList(ListNode* head) {
// 遍历原链表,使用头插法
// 虚拟头节点
ListNode* DummyHead=new ListNode();
ListNode* cur=head;
while(cur!=nullptr){
ListNode* tmp=new ListNode(cur->val);
tmp->next=DummyHead->next;
DummyHead->next=tmp;
cur=cur->next;
}
return DummyHead->next;
}
};
方法二:
/**
* Definition for singly-linked list.
* struct ListNode {
* int val;
* ListNode *next;
* ListNode() : val(0), next(nullptr) {}
* ListNode(int x) : val(x), next(nullptr) {}
* ListNode(int x, ListNode *next) : val(x), next(next) {}
* };
*/
class Solution {
public:
ListNode* reverseList(ListNode* head) {
// 双指针法直接翻转
ListNode* temp; // 保存cur的下一个节点
ListNode* cur = head;
ListNode* pre = nullptr;
while(cur!=nullptr){
temp=cur->next; // 保存一下 cur的下一个节点,因为接下来要改变cur->next
cur->next=pre;// 翻转操作
// 更新pre 和 cur指针
pre=cur;
cur=temp;
}
return pre;
}
};
Python版:
方法一:
# Definition for singly-linked list.
# class ListNode:
# def __init__(self, val=0, next=None):
# self.val = val
# self.next = next
class Solution:
def reverseList(self, head: Optional[ListNode]) -> Optional[ListNode]:
DummyHead=ListNode()
cur=head
while cur:
tmp=ListNode(cur.val)
tmp.next=DummyHead.next
DummyHead.next=tmp
cur=cur.next
return DummyHead.next
方法二:
# Definition for singly-linked list.
# class ListNode:
# def __init__(self, val=0, next=None):
# self.val = val
# self.next = next
class Solution:
def reverseList(self, head: Optional[ListNode]) -> Optional[ListNode]:
cur=head
pre=None
while cur:
tmp=cur.next
cur.next=pre
pre=cur
cur=tmp
return pre
需要注意的地方
1.方法一定义了新的链表,需要更多的空间资源,是对内存空间的浪费,方法二直接进行链表翻转,比方法一更优。
2.方法二中,更新pre和cur的时候需要先移动pre指针,再移动cur指针。