1. 程式人生 > 其它 >劍指offer程式碼解析——面試題17合併兩個排序的連結串列

劍指offer程式碼解析——面試題17合併兩個排序的連結串列

本題的詳細解析均在程式碼註釋中:

/**
 * 題目:輸入兩個遞增排序的連結串列,合併這兩個連結串列並使新連結串列中的結點仍然是按照遞增排序的。
 * @author 大閒人柴毛毛
 * @date 2016年3月14日
 */
public class MergeLink {
	/**
	 * 分析:我們把兩個單鏈表分為a1、a2,每次從a2中取出頭結點,然後在a1中尋找插入點插入,重複上述操作直到a2中結點被取光為止。
	 * 程式碼如下:
	 */
	
	/**
	 * 合併兩個遞增的單鏈表
	 * @param first1 第一個連結串列的頭結點
	 * @param first2 第二個連結串列的頭結點
	 * @return 返回合併後連結串列的頭結點
	 */
	public static Node<Integer> mergeLink(Node<Integer> first1, Node<Integer> first2){
		//若a1為空,a2為空
		if(first1==null && first2==null){
			System.out.println("兩個連結串列均為空!");
			return null;
		}
		
		//若a1為空,a2不為空,則返回a2
		if(first1==null && first2!=null)
			return first2;
		
		//若a2為空,a1不為空,則返回a1
		if(first1!=null && first2==null)
			return first1;
		
		//若a1、a2均不為空,則進行合併
		while(first2!=null){
			//p指向連結串列一中的當前結點
			Node<Integer> p = first1;
			
			//若first2<p,則將first2插入到p之前
			if(first2.data < p.data){
				//q指向first2
				Node<Integer> q = first2;
				//first2指向後繼結點
				first2 = first2.next;
				//將a2的頭結點摘下來,裝到a1的頭上
				q.next = p;
				first1 = q;
			}
			
			//若first2>=p時,p一直向後找,直到找到first2<p時停止,將first2插入到p的前面
			Node<Integer> p_pre = p;//p_pre指向p的前一個結點
			while(p.data<=first2.data && p!=null){
				p_pre = p;
				p = p.next;
			}
			//q指向first2
			Node<Integer> q = first2;
			//first2指向後繼結點
			first2 = first2.next;
			//q的後繼結點設為p
			q.next = p;
			//p_pre的後繼結點設為q
			p_pre.next = q;
		}
		
		return first1;
	}
}


/**
 * 定義結點 
 */
class Node<T>{
	public T data;
	public Node<T> next;
}