合并 k 个排序链表,返回合并后的排序链表。请分析和描述算法的复杂度。
示例:
输入:
[
1->4->5,
1->3->4,
2->6
]
输出: 1->1->2->3->4->4->5->6
方法:累加法
思路:
1,k个相加其实简化就是两两相加,将数组前两个相加,再逐一往后相加即可;
2,具体思路还是两个链表合并,参考合并两个有序链表
3,需要把数组每个元素都操作一次,所以时间复杂度为 O(n) ,空间复杂度为 O(1);
class Solution {
public ListNode mergeKLists(ListNode[] lists) {
//合并两个的扩展
ListNode res = new ListNode(0);
if (lists == null || lists.length == 0) return res.next;
else if (lists.length == 1) return lists[0];
else if (lists.length == 2) return mergeTwo(lists[0],lists[1]);
else {
res = mergeTwo(lists[0],lists[1]);
for (int i = 2; i < lists.length; i ++) {
res = mergeTwo(res,lists[i]);
}
return res;
}
}
public ListNode mergeTwo(ListNode l1, ListNode l2) {
//定义结果
ListNode res = new ListNode(0);
//定义临时头指针结点指向结果
ListNode temp = res;
//遍历两个链表
while (l1 != null && l2 != null) {
//比较两个链表的值
if (l1.val < l2.val ) {
//临时头结点指向l1
temp.next = l1;
//l1的节点往后走一步
l1 = l1.next;
} else {//否则改变l2
temp.next = l2;
l2 = l2.next;
}
//临时头结点往后走一步(因为已经存了一个值了)
temp = temp.next;
}
//两个链表长度不一样,需要补全
if (l1 != null)
temp.next = l1;
else if (l2 != null)
temp.next = l2;
//结果的头结点是哑结点
return res.next;
}
}
注意:对特殊情况的判断操作!数组为空时返回空链表!!!