Leetcode 206:反转链表
题目描述
反转一个单链表。
示例:
输入: 1->2->3->4->5->NULL
输出: 5->4->3->2->1->NULL
进阶:
你可以迭代或递归地反转链表。你能否用两种方法解决这道题?
我的解法一:用map做临时存储
两次循环,第一次把链表中的数据存储到map里,第二次倒序遍历map的key值,存进链表。
ListNode* reverseList(ListNode* head) {
map<int, int> m;
int i = 0;
ListNode* p = head;
while(p != NULL)
{
m[i++] = p->val;
p = p->next;
}
p = head;
while(p != NULL)
{
p->val = m[--i];
p = p->next;
}
return head;
我的解法二:后值前插法(我起的名字)
具体操作是遍历链表,第一步先把链表头指针即第一个节点next指向第三个节点,再把第二个节点的next指向第一个节点。再对第三个节点执行相同操作。以此类推,直到head->next为NULL。
ListNode* reverseList(ListNode* head) {
if(head == NULL){return head;}
ListNode* p = head;
ListNode* q = head->next;
while(head->next != NULL)
{
q = head->next;
head->next = q->next;
q->next = p;
p = q;
}
return p;
}
迭代法
相当于是我的解法之上的升级版,除了进行head->next 指向NULL操作之外,第一步是把第二个节点指针指向第一个节点再以此类推,而省去了第一个节点指向第三个节点的过程(因为第三个节点用一个新节点指针定义了,不会出现找不到的问题)
ListNode* newhead = NULL;
while(head != NULL)
{
ListNode* t = head->next;
head->next = newhead;
newhead = head;
head = t;
}
return newhead;
}
递归法
ListNode* reverseList(ListNode* head) {
if(!head || !head->next){return head;}
ListNode* newHead = reverseList(head->next);
head->next->next = head;
head->next = NULL;
return newHead;
}
不好理解?把一层层的嵌套展开,写一个伪码方便理解:
/*
* for example
* 1->2->3->4->NULL
*/
ListNode* reverseList(ListNode* head) {
if (!head || !head->next) return head; // 1
//ListNode *newHead = reverseList(head->next); // 1
if (!head2 || !head2->next) return head2; // 2
//ListNode *newHead = reverseList(head->next); //2
if (!head3 || !head3->next) return head3; // 3
//ListNode *newHead = reverseList(head->next); //3
if (!head4 || !head4->next) return head4; // The last
head3->next->next = head3; //3
head3->next = NULL; //3
return newHead; //3
head2->next->next = head2; //2
head2->next = NULL; //2
return newHead; //2
head->next->next = head; // 1
head->next = NULL; // 1
return newHead; // 1
}
};