前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >【LeetCode每日一题】23. Merge k Sorted Lists

【LeetCode每日一题】23. Merge k Sorted Lists

作者头像
公众号-不为谁写的歌
发布2020-07-25 17:01:38
2720
发布2020-07-25 17:01:38
举报
文章被收录于专栏:桃花源记桃花源记

题目描述

Merge k sorted linked lists and return it as one sorted list. Analyze and describe its complexity.

Example:

代码语言:javascript
复制
Input:
[
  1->4->5,
  1->3->4,
  2->6
]
Output: 1->1->2->3->4->4->5->6

合并k个有序单链表,然后返回这个新链表。分析时间复杂度、空间复杂度。

题解

暴力破解

将链表转换成数组,然后将数组排序,最后根据数组中的顺序依次生成结果链表中的节点。

代码语言:javascript
复制
/**
 * 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* mergeKLists(vector<ListNode*>& lists) {
        if (lists.empty()) return nullptr;
        vector<int> arr;
        
        for (ListNode* list : lists){
            while (list){
                arr.push_back(list->val);
                list = list->next;
            }
        }
        sort(arr.begin(), arr.end());
        ListNode *first = new ListNode(-1), *node = first;
        
        for (int val : arr){
            node->next = new ListNode(val);
            node = node->next;
        }
        
        return first->next;
    }
};

时间复杂度:O(NlogN)

空间复杂度:O(N).

优先队列

同时进行k个链表的合并,通过将每个链表的头结点放入优先队列中(同时完成了排序),弹出节点,将节点并入结果链表中,如果当前节点仍不为空,则将下一个节点压入优先队列中。

代码语言:javascript
复制
/**
 * 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) {
        auto cmp = [](ListNode* &l1, ListNode* &l2){
            return l1->val > l2->val;
        };
        // 定义一个小顶堆
        priority_queue<ListNode*, vector<ListNode*>, decltype(cmp) > q(cmp);
        
        for (auto node: lists){
            if(node) q.push(node);
        }
        ListNode* dummy = new ListNode(-1), *cur = dummy;
        
        while (!q.empty()){
            auto t = q.top(); q.pop();
            cur->next = t;
            cur = cur->next;
            if (t->next) q.push(t->next);
        }
        
        return dummy->next;
    }
};

时间复杂度:O(Nlogk)

空间复杂度:O(N)新链表所用空间;O(k)优先队列所占空间。

两两合并

类似于分治法,不断进行两两合并,直到只剩最后一个链表,这个链表就为最终的结果链表。

代码语言:javascript
复制
/**
 * 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* mergeKLists(vector<ListNode*>& lists) {
        if (lists.empty()) return nullptr;
        
        int size = lists.size();
        
        while (size > 1){
            int k = (size + 1)/2;
            for (int i=0; i< size/2; i++)
                lists[i] = merge(lists[i], lists[i+k]);
            size = k;
        }
        
        return lists[0];
    }
private:
    ListNode* merge(ListNode *l1, ListNode *l2){
        ListNode *first = new ListNode(-1);
        ListNode *node = first;
        
        while(l1 && l2){
            if (l1->val < l2->val){
                node->next = l1;
                l1 = l1->next;
            }
            else{
                node->next = l2;
                l2 = l2->next;
            }
            node = node->next;
        }
        if (l1) node->next = l1;
        if (l2) node->next = l2;
        
        return first->next;
    }
};

时间复杂度:O(Nlogk)

空间复杂度:O(1)

References

https://leetcode.com/problems/merge-k-sorted-lists/solution/


本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2020-07-23 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 题目描述
  • 题解
    • 暴力破解
      • 优先队列
        • 两两合并
          • References
          领券
          问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档