合并 k 个排序链表,返回合并后的排序链表。请分析和描述算法的复杂度。
输入: [ 1->4->5, 1->3->4, 2->6 ]
输出: 1->1->2->3->4->4->5->6
方法一:归并法
思想:
借助归并排序的思想,对两两链表进行归并。结束条件为链表数量为1。
//合并两条链表
ListNode* mergeTwoLists(ListNode* l1, ListNode* l2) {
if (l1 == NULL && l2 == NULL)
return NULL;
else if (l1 == NULL)
return l2;
else if (l2 == NULL)
return l1;
else {
ListNode* dummyHead = new ListNode(-1); //假的头节点
ListNode* q = l1, *p = l2, *t = dummyHead;
while (q != NULL && p != NULL) {
if (q->val < p->val) {
t->next = q;
q = q->next;
}
else {
t->next = p;
p = p->next;
}
t = t->next;
}
if (q != NULL) { //q不为空,说明l1未遍历完,但l2肯定遍历完了
t->next = q;
}
else {
t->next = p;
}
return dummyHead->next;
}
}
//合并K条链表
ListNode* mergeKLists(vector<ListNode*>& lists) {
if (lists.size() == 0)
return NULL;
else if (lists.size() == 1)
return lists[0];
else {
int length = lists.size(); //链表数量
int count = 0;
//当容器长度为1说明已经合并完
while (length > 1) {
if (length % 2 == 0) { //偶数条链表
for (int i = 0;i < length - 1;i = i + 2) {
//将合并后的链表重新赋予链表容器中
lists[count] = mergeTwoLists(lists[i], lists[i + 1]);
++count;
}
}
else {
for (int i = 0;i < length - 2;i = i + 2) {
lists[count] = mergeTwoLists(lists[i], lists[i + 1]);
++count;
}
lists[count++] = lists[length - 1];
}
length = count;
count = 0;
}
}
return lists[0];
}