leetcode 206. 反转链表 及 92. 反转链表 II

206. 反转链表

问题描述

反转一个单链表。
示例:
输入: 1->2->3->4->5->NULL
输出: 5->4->3->2->1->NULL
进阶:
你可以迭代或递归地反转链表。你能否用两种方法解决这道题?

问题分析

开始我们定义一个虚拟的头结点a,他的下一个节点为head.假设我们到了某一步已经反转了一些元素:a->[], b->c->d->...,其中[]中是已经反转好的元素,b->c->d->...是待反转的元素,下一步我们要做的只是把b插到a与[]之间即可。先用c记录b的下一个结点(c=b->next),也是下一个待插的节点。令b->next指向a->next(b->next = a->next),令a->next指向b(a->next = b),注意顺序不可换,则b就插到a与[]之间了:a->b->[],c->d->...,然后把下一个待插元素c赋值给b,只要b不空,就继续插。

代码

//迭代方法
/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode(int x) : val(x), next(NULL) {}
 * };
 */
class Solution {
public:
    ListNode* reverseList(ListNode* head) {
        ListNode* a = new ListNode(0);
        a->next = NULL;
        ListNode *b = head,*c;
        while(b != NULL)
        {
            c = b->next;
            b->next = a->next;
            a->next = b;           
            b = c;
        }
        b = a->next;
        delete a;
        return b;
        
    }
};

或者

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode(int x) : val(x), next(NULL) {}
 * };
 */
class Solution {
public:
    ListNode* reverseList(ListNode* head) {
        if(head == NULL) return NULL;
        ListNode* a = new ListNode(0);
        a->next = head;
        ListNode *b = head,*c=b->next;
        while(b->next != NULL)
        {
            c = b->next;
            b->next = c->next;
            c->next= a->next;
            a->next = c;           
        }
        b = a->next;
        delete a;
        return b;
        
    }
};

92. 反转链表 II

问题描述

反转从位置 m 到 n 的链表。请使用一趟扫描完成反转。
说明:
1 ≤ m ≤ n ≤ 链表长度。
示例:
输入: 1->2->3->4->5->NULL, m = 2, n = 4
输出: 1->4->3->2->5->NULL

问题分析

注意这道题第二部分的迭代和上一道题完全反转的迭代不同,上一道题相当于另外开了一个链表,然后一直往头结点和第二个节点之间添加元素。但是这道题在反转完成后还需要和后面不反转的连在一起,因此是相当于在原先链表上做。

代码

/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     ListNode *next;
 *     ListNode(int x) : val(x), next(NULL) {}
 * };
 */
class Solution {
public:
    ListNode* reverseBetween(ListNode* head, int m, int n) {
        ListNode *dummy = new ListNode(0);
        dummy->next = head;
        ListNode *a = dummy,*b,*c;
        int k = n-m;
        while(--m > 0)
        {
            a = a->next;
        }
        b = a->next;
        while(k-- >0)
        {
            c = b->next;
            b->next = c->next;
            c->next = a->next;
            a->next = c;
        }
        b = dummy->next;
        delete dummy;
        return b;
    }
};
posted @ 2019-11-29 15:58  曲径通霄  阅读(137)  评论(0编辑  收藏  举报