• Merge k Sorted Lists


    题目链接

    Merge k Sorted Lists - LeetCode

    注意点

    • 给出了链表是有序的

    解法

    解法一:暴力。用map收集所有链表的数据,然后排序生成新链表。时间复杂度O(kn)

    /**
     * Definition for singly-linked list.
     * struct ListNode {
     *     int val;
     *     ListNode *next;
     *     ListNode(int x) : val(x), next(NULL) {}
     * };
     */
    class Solution {
    public:
        ListNode* mergeKLists(vector<ListNode*>& lists) {
            map<int,int> m;
            int max = -2147483648;
            int min = 2147483647;
            for(auto l:lists)
            {
                auto p = l;
                while(p != NULL)
                {
                    if(p->val > max) max = p->val;
                    if(p->val < min) min = p->val;
                    if(m.count(p->val) == 0) m[p->val] = 1;
                    else m[p->val]++;
                    p = p->next;
                }
            }
            ListNode* ret = new ListNode(0);
            auto p = ret;
            for(auto i = min;i <= max;i++)
            {
                int temp = m.count(i);
                if(temp != 0)
                {
                    temp = m[i];
                    for(auto j = 0;j < temp;j++)
                    {
                        p->next = new ListNode(i);
                        p = p->next;
                    }
                }
            }
            return ret->next;
        }
    };
    

    解法二:分治法。比如6个链表,先合并14、25、36。然后合并13,最后和2合并即可。要用到Merge Two Sorted Lists的函数。时间复杂度O(nlogk)。

    class Solution {
    public:
        ListNode *mergeKLists(vector<ListNode *> &lists) {
            if (lists.size() == 0) return NULL;
            int n = lists.size();
            while (n > 1) 
            {
                int k = (n + 1) / 2;
                for (int i = 0; i < n / 2; i++) 
                {
                    lists[i] = mergeTwoLists(lists[i], lists[i + k]);
                }
                n = k;
            }
            return lists[0];
        }
        
        ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
            ListNode* ans = new ListNode(0);
            ListNode* pointer = ans;
            while(l1 != NULL && l2 != NULL)
            {
                if(l1->val < l2->val)
                {
                    pointer->next = l1;
                    pointer = pointer->next;
                    l1 = l1->next;
                }
                else
                {
                    pointer->next = l2;
                    pointer = pointer->next;
                    l2 = l2->next;
                }
            }
            if(l1 != NULL)
            {
                pointer->next = l1;
            }
            if(l2 != NULL)
            {
                pointer->next = l2;
            }
            return ans->next;
        }
    };
    

    解法三:优先队列(或者叫最小堆)。参见[LeetCode] Merge k Sorted Lists 合并k个有序链表

    小结

    • 暴力算法真是万能的!
  • 相关阅读:
    装饰器api
    API
    Python之模块和包
    编辑后保留原URl搜索条件
    数据结构相关知识
    博客系统之评论树与评论楼相关操作
    Redis五大数据类型以及操作
    Class python31
    python_class21
    数字及字符串
  • 原文地址:https://www.cnblogs.com/multhree/p/10356133.html
Copyright © 2020-2023  润新知