美文网首页
23. 合并K个排序链表

23. 合并K个排序链表

作者: oneoverzero | 来源:发表于2020-02-02 11:31 被阅读0次

题目描述:

合并 k 个排序链表,返回合并后的排序链表。请分析和描述算法的复杂度。

示例:

输入:
[
  1->4->5,
  1->3->4,
  2->6
]
输出: 1->1->2->3->4->4->5->6

优先级队列的概念:

参考:

优先级队列与普通队列一样,只能从队尾插入元素,从队首删除元素。但是它有一个特性,就是队列中最大的元素总是位于队首,所以出队时,并非按照先进先出的原则进行,而是将当前队列中最大的元素出队。优先级队列底层是用堆实现的。

Python的PriorityQueue是用 heapq 实现的。( https://blog.csdn.net/liu2012huan/article/details/53264162

代码:

from Queue import PriorityQueue
# Definition for singly-linked list.
# class ListNode(object):
#     def __init__(self, x):
#         self.val = x
#         self.next = None

class Solution(object):
    def mergeKLists(self, lists):
        """
        :type lists: List[ListNode]
        :rtype: ListNode
        """
        q = PriorityQueue(maxsize=len(lists))
        cur = dummy = ListNode(None)
        for idx, node in enumerate(lists):
            if node:
                q.put((node.val, idx, node))
        while q.qsize() > 0:
            _, idx, cur.next = q.get() # get()会将节点弹出
            cur = cur.next
            if cur.next:
                q.put((cur.next.val, idx, cur.next))
        return dummy.next

这里有一些细节需要注意:

  • 优先级队列需要明确将哪个量设置为优先级的评价标准,这里 node.val 就是用来作为这一标准的;
  • 为什么还要引入 idx ?这是因为如果“第一评价标准”的优先级相同(这里即为 node.val ),代码就会比较“第二评价标准”。这里如果不设置“第二评价标准”,代码便会将 node 作为“第二评价标准”,而 node 是一个节点类,可能没有重写比较的方法,此时代码就会报错(这便是在 https://leetcode.com/problems/merge-k-sorted-lists/discuss/10511/10-line-python-solution-with-priority-queue 中 @ __fibo__ 提到的问题)。因此必须要找一个辅助变量作为“第二评价标准”,这里选取的是节点在列表中的索引。

复杂度分析:(强烈建议参考: https://blog.csdn.net/hellozhxy/article/details/81055397

前已述及,优先级队列的底层是用堆实现的。因此往一个长度为 n 的优先级队列中插入一个元素的时间复杂度为 O(\log n) 。如果总共有 m 个元素,则将这 m 个元素插入这个长度为 n 的优先级队列中的时间复杂度为 O(m \log n)

现在代码中优先级队列的最大长度为 k ,把最初的 k 个头结点插入这个优先级队列的时间复杂度为 O(k \log k)

关于时间复杂度的分析,@ gulshan98125 认为:假设 n 是所有链表中最长的链表长度,现在总共有 k 个链表,则总的时间复杂度为 O(nk \log k) ;而 @spitza 认为,把 n 当成是 k 个链表中所有的节点个数显得更直观一些,这样一来时间复杂度将会变成 O(n \log k) 。我个人的观点是,把 n 当成是这 k 个链表的平均长度,这样时间复杂度为 O(nk \log k)

空间消耗在于维护一个长度为 k 的优先级队列(其实是维护一个容量为 k 的堆),因此空间复杂度为 O(k)

相关文章

  • LeetCode 专题 :分治算法

    LeetCode 第 23 题:归并多个有序链表 传送门:23. 合并K个排序链表。 合并 k 个排序链表,返回合...

  • 23. 合并K个排序链表

    23.合并K个排序链表 合并k个排序链表,返回合并后的排序链表。请分析和描述算法的复杂度。 示例: 输入:[ 1-...

  • 【LeetCode】23.合并K个排序链表

    题目描述 23.合并K个排序链表 合并k个排序链表,返回合并后的排序链表。请分析和描述算法的复杂度。 题目解析 方...

  • leecode刷题(27)-- 合并k个排序链表

    leecode刷题(27)-- 合并k个排序链表 合并k个排序链表 合并 k 个排序链表,返回合并后的排序链表。请...

  • 23. 合并K个排序链表

    23. 合并K个排序链表 题目链接:https://leetcode-cn.com/problems/merge-...

  • TOP HOT 100 题

    23. 合并多个排序链表:https://leetcode-cn.com/problems/merge-k-sor...

  • ARTS第五周2020620

    Algorithm 合并K个排序链表 合并 k 个排序链表,返回合并后的排序链表。请分析和描述算法的复杂度。 示例...

  • 合并K个排序链表【LeetCode:23】

    题目: 合并K个排序链表 合并 k 个排序链表,返回合并后的排序链表。请分析和描述算法的复杂度。 示例: 输入: ...

  • Swift - LeetCode - 合并K个排序链表

    题目 合并K个排序链表 问题: 合并 k 个排序链表,返回合并后的排序链表。请分析和描述算法的复杂度。 解题思路:...

  • LeetCode:合并K个排序链表

    合并K个排序链表(困难) 题目叙述: 合并 k 个排序链表,返回合并后的排序链表。请分析和描述算法的复杂度。 示例...

网友评论

      本文标题:23. 合并K个排序链表

      本文链接:https://www.haomeiwen.com/subject/toafxhtx.html