package algorithm;
import java.util.List;
/*
原题
Merge k sorted linked lists and return it as one sorted list. Analyze and describe its complexity.
题目大意
合并k个排好的的单链表。分析和描述它的复杂性。
*/
public class mergeKNum {
//采用归并排序的思想
//时间复杂度是O(logn),合并两个链表的时间复杂度是O(n),则总的时间复杂度大概是O(nlogn)
public ListNode mergeKSortedList(ListNode[] list){
if(list==null||list.length==0)
return null;
if(list.length==1){ //只有一个
return list[0];
}
//至少2个节点
int begin=0; //开始索引
int end=list.length-1; //结束索引
while(end>0){
begin=0;
while(end>begin){
list[begin]=merge(list[begin],list[end]);
begin++;
end--;
}
}
return list[0];
}
/*
* 辅助类
*/
class ListNode {
int value;// 值
ListNode nextNode; // 下一个节点
ListNode(int value) {
this.value = value;
this.nextNode = null;
}
}
/*
* 数组变成链表对象输入:整型数组输出:链表对象
*/
ListNode buildListNode(int[] input) {
ListNode first = null, last = null;
if (input == null) {
return null;
}
ListNode newNode;
for (int i = 0; i < input.length; i++) {
newNode = new ListNode(input[i]);
if (first == null) {// 开始为空
first = newNode;
last = newNode;
} else {
last.nextNode = newNode;
last = newNode;
}
}
return first;
}
public void printNode(ListNode node) {
ListNode node1 = node;
System.out.println("---------------");
while (node1 != null) {
System.out.print(" " + node1.value);
node1 = node1.nextNode;
}
System.out.println("\n---------------");
}
public ListNode merge(ListNode node1, ListNode node2) {
if (node1 == null)
return node2;
if (node2 == null)
return node1;
ListNode root = null;
ListNode tmp = null;
do { // node1和node2均不为空
int value1 = node1.value;
int value2 = node2.value;
if (value2 > value1) {// vaule1小 ,添加node1
if (root == null) {// 首次
root = node1;
} else {
tmp.nextNode = node1;
}
tmp = node1;
node1 = node1.nextNode;
} else {// value2小,添加node2
if (root == null) {// 首次
root = node2;
} else {
tmp.nextNode = node2;
}
tmp = node2;
node2 = node2.nextNode;
}
} while (node1 != null && node2 != null);
while (node1 != null) {
tmp.nextNode = node1;
tmp = node1;
node1 = node1.nextNode;
}
while (node2 != null) {
tmp.nextNode = node2;
tmp = node2;
node2 = node2.nextNode;
}
return root;
}
//https://blog.csdn.net/DERRANTCM/article/details/47016121
public ListNode mergeTwoLists(ListNode l1, ListNode l2) {
ListNode head = new ListNode(0); // 创建一个头结点,最后还要删除掉
ListNode tail = head;
while (l1 != null && l2 != null) {
if (l1.value <= l2.value) {
tail.nextNode = l1;
l1 = l1.nextNode;
} else {
tail.nextNode = l2;
l2 = l2.nextNode;
}
tail = tail.nextNode; // 移动到新的尾结点
}
tail.nextNode = (l1 != null ? l1 : l2);
return head.nextNode; // head的下一个节点是第一个数据结点 } }
}
public static void main(String[] args) {
mergeKNum mkn = new mergeKNum();
ListNode[] list = new ListNode[4];
int[] tmp1 = { 1, 5, 9 };
ListNode node1 = mkn.buildListNode(tmp1);
// mkn.printNode(node);
int[] tmp2 = { 2, 6, 10 };
ListNode node2 = mkn.buildListNode(tmp2);
int[] tmp3 = { 3, 7, 11 };
ListNode node3=mkn.buildListNode(tmp3);
int[] tmp4 = { 4, 8, 12 };
ListNode node4=mkn.buildListNode(tmp4);
list[0]=node1;
list[1]=node2;
list[2]=node3;
list[3]=node4;
ListNode nodeShow=mkn.mergeKSortedList(list);
mkn.printNode(nodeShow);
/*
ListNode node3 = mkn.merge(node1, node2);
System.out.println("node1信息如下:");
mkn.printNode(node1);
System.out.println("node2信息如下:");
mkn.printNode(node2);
System.out.println("合并后为:");
mkn.printNode(node3);
*/
}
}