LeetCode – Merge k Sorted Lists (Java)

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

Analysis

The simplest solution is using PriorityQueue. The elements of the priority queue are ordered according to their natural ordering, or by a comparator provided at the construction time (in this case).

Java Solution

public ListNode mergeKLists(ListNode[] lists) {
    if(lists==null||lists.length==0)
        return null;
 
    PriorityQueue<ListNode> queue = new PriorityQueue<ListNode>(new Comparator<ListNode>(){
        public int compare(ListNode l1, ListNode l2){
            return l1.val - l2.val;
        }
    });
 
    ListNode head = new ListNode(0);
    ListNode p = head;
 
    for(ListNode list: lists){
        if(list!=null)
            queue.offer(list);
    }    
 
    while(!queue.isEmpty()){
        ListNode n = queue.poll();
        p.next = n;
        p=p.next;
 
        if(n.next!=null)
            queue.offer(n.next);
    }    
 
    return head.next;
 
}

Time: log(k) * n.
k is number of list and n is number of total elements.

Category >> Algorithms  
If you want someone to read your code, please put the code inside <pre><code> and </code></pre> tags. For example:
<pre><code> 
String foo = "bar";
</code></pre>

  1. IsAlright on 2014-4-19

    By doing this you are introducing an extra log(n) factor to your runtime.

  2. Guest on 2014-5-13

    No.. the factor is log(k)

  3. Meeeeee on 2014-11-3

    I think your algorism is wrong.

    why you hard coded the head node as :

    ListNode head = new ListNode(0);

    if you “return head.next”, you will return null!

    And I don’t understand why you write the following , could you explain more? you already write q.add(list), why you write “q.add(temp.next)” again? what’s you purpose?

    //keep adding next element of each list
    if (temp.next != null)
    q.add(temp.next);

    ———————————————–

    ListNode head = new ListNode(0);
    ListNode p = head; // serve as a pointer/cursor

    while (q.size() > 0) {
    ListNode temp = q.poll();
    //poll() retrieves and removes the head of the queue – q.
    p.next = temp;

    //keep adding next element of each list
    if (temp.next != null)
    q.add(temp.next);

    p = p.next;
    }

    return head.next;,

  4. Guest on 2015-3-5

    Yes, the algorithm is perfectly correct.
    The head node is just a helper so you can start arranging the sorted list.

  5. Pallavi on 2016-2-8

    Thanks for sharing this. One question – Shouldn’t the time complexity by (nklog(k)), because ultimately we end up removing O(nk) elements from the priority queue, each time the work being O(log(k))

  6. Yanfei on 2016-6-26

    No, it is n*log(k) since n is the number of total elements.

  7. Neel on 2016-8-27

    What is the purpose of the following statement:

    queue.offer(n.next);

  8. nebula on 2016-9-6

    we need to put the remain list to the queue again.

Leave a comment

*