1. 程式人生 > 其它 >VC++6.0 回車對話方塊介面關閉

VC++6.0 回車對話方塊介面關閉

160.相交連結串列

由題目要求可以知道,題目資料保證了不會出現環形

注意,函式返回結果後,連結串列必須 保持其原始結構

方法一:雜湊集合

利用雜湊表的特性,不能放重複元素

判斷兩個連結串列是否相交,可以將結點儲存在雜湊集合裡,因為雜湊集合裡的元素是不允許重複的

首先遍歷連結串列 headA,將連結串列 headA 中的元素加入雜湊集合中,然後遍歷 headB,對於遍歷的結點,判斷該節點是否已經新增過

  • 如果當前節點不在雜湊集合中,繼續下一個節點
  • 如果在集合中,該節點就是相交的節點,返回即可
  • 如果 headB 中的所有節點都不在,則兩個連結串列不相交,返回 null
public class Solution {
	public ListNode getIntersectionNode(ListNode headA, ListNode headB) {
    	if (headA == null || headB == null) {
            return null;
        }
        Set<ListNode> visited = new HashSet<>();
        ListNode h = headA;
        while (h != null) {
        	visited.add(h);
            h = h.next;
        }
        h = headB;
        while (h != null) {
            // 這個也可以滿足條件
        	//if (visited.contains()) {
            //	return h;
            //}
            
        	if (!visited.add(h)) {
                return h;
            }
            h = h.next;
        }
        return null;
    }
}

方法二:雙指標

使用雙指標可以將空間複雜度降到 O(1)

只有當 headA 和 headB 都不為空時,兩個連結串列才會相交,所以先判斷連結串列是否為空

當連結串列 headA 和 headB 都不為空時,建立兩個指標pA,pB,分別從 headA 和 headB開始,遍歷連結串列,操作如下:

  • 每步都需要同時更新指標 pA 和 pB
  • 如果 pA 不為空,則移向下一個節點;如果為空,則將指標 pA 移到連結串列 headB 的頭結點
  • 如果 pB 不為空,則移向下一個節點;如果為空,則將指標 pB 移到連結串列 headA 的頭結點
  • 當指標 pA 和 pB 指向同一個節點或者都為空時,返回他們指向的結點或null
public class Solution {
	public ListNode getIntersectionNode(ListNode headA, ListNode headB) {
    	if (headA == null || headB == null) {
        	return null;
        }
        ListNode pA = headA, pB = headB;
        while (pA != pB) {
        	pA = pA == null ? headB : pA.next;
            pB = pB == null ? headA : pB.next;
        }
        return pA;
    }
}