• 148. Sort List


    Sort a linked list in O(n log n) time using constant space complexity.

    Example 1:

    Input: 4->2->1->3
    Output: 1->2->3->4
    

    Example 2:

    Input: -1->5->3->4->0
    Output: -1->0->3->4->5

    AC code:

    time(O(nlongn)  space(O(logn))

    /**
     * Definition for singly-linked list.
     * struct ListNode {
     *     int val;
     *     ListNode *next;
     *     ListNode(int x) : val(x), next(NULL) {}
     * };
     */
    class Solution {
    public:
        ListNode* sortList(ListNode* head) {
            if (head == NULL || head->next == NULL) return head;
            ListNode* fast = head->next;
            ListNode* slow = head;
            while (fast != NULL && fast->next != NULL) {
                fast = fast->next->next;
                slow = slow->next;
            }
            ListNode* mid = slow->next;
            slow->next = NULL;
            return merge(sortList(head), sortList(mid));
        }
    private:
        ListNode* merge(ListNode* l1, ListNode* l2) {
            ListNode dummy(0);
            ListNode* p = &dummy;
            while (l1 && l2) {
                if (l1->val > l2->val) swap(l1, l2);
                p->next = l1;
                l1 = l1->next;
                p = p->next;
            }
            if (l1) p->next = l1;
            if (l2) p->next = l2;
            return dummy.next;
        }
    };
    

    Runtime: 28 ms, faster than 100.00% of C++ online submissions for Sort List.

    optimization code:

    time:O(nlongn))  space:O(1)

    // Author: Huahua
    // Running time: 32 ms
    class Solution {
    public:
      ListNode* sortList(ListNode* head) {
        // 0 or 1 element, we are done.
        if (!head || !head->next) return head;
        
        int len = 1;
        ListNode* cur = head;
        while (cur = cur->next) ++len;
        
        ListNode dummy(0);
        dummy.next = head;
        ListNode* l;
        ListNode* r;
        ListNode* tail;
        for (int n = 1; n < len; n <<= 1) {      
          cur = dummy.next; // partial sorted head
          tail = &dummy;
          while (cur) {
            l = cur;
            r = split(l, n);
            cur = split(r, n);
            auto merged = merge(l, r);
            tail->next = merged.first;
            tail = merged.second;
          }
        }      
        return dummy.next;
      }
    private:
      // Splits the list into two parts, first n element and the rest.
      // Returns the head of the rest.
      ListNode* split(ListNode* head, int n) {    
        while (--n && head)
          head = head->next;
        ListNode* rest = head ? head->next : nullptr;
        if (head) head->next = nullptr;
        return rest;
      }
      
      // Merges two lists, returns the head and tail of the merged list.
      pair<ListNode*, ListNode*> merge(ListNode* l1, ListNode* l2) {
        ListNode dummy(0);
        ListNode* tail = &dummy;
        while (l1 && l2) {
          if (l1->val > l2->val) swap(l1, l2);
          tail->next = l1;
          l1 = l1->next;
          tail = tail->next;
        }
        tail->next = l1 ? l1 : l2;
        while (tail->next) tail = tail->next;
        return {dummy.next, tail};
      }
    };
    

      

    永远渴望,大智若愚(stay hungry, stay foolish)
  • 相关阅读:
    Docker(五)-Dcoker容器
    Docker(二)-Docker安装
    Docker(四)-Dcoker镜像
    Docker(三)-Docker中Image、Container与Volume的迁移
    Docker(一)-Docker介绍
    coredump分析
    linux下生成core dump文件方法
    软件测试流程清单
    软件测试风险清单
    [测试管理]测试周报该如何写
  • 原文地址:https://www.cnblogs.com/h-hkai/p/9872561.html
Copyright © 2020-2023  润新知