题目
两个链表的交叉
请写一个程序,找到两个单链表最开始的交叉节点。
样例
下列两个链表:
A: a1 → a2
↘
c1 → c2 → c3
↗
B: b1 → b2 → b3
在节点 c1 开始交叉。
注意
- 如果两个链表没有交叉,返回
null
。 - 在返回结果后,两个链表仍须保持原有的结构。
- 可假定整个链表结构中没有循环。
挑战
Python Code
Java Code
需满足 O(n) 时间复杂度,且仅用 O(1) 内存。
解题
尝试用时间复杂度是O(NM),却没有解决,在这个博客看到根据两个链表的特性进行解决。
就如同上图,两个链表相交的部分一定在尾部的,如果两个链表尾部对齐,按照短的链表头节点开始,同时时对两个链表进行遍历,找到相同节点处就是共同的节点。
这里为了找到短链表的都节点在长链表处的位置<这里的位置是相对的,他们不一定是在一起的,这里只是为了让尾对齐>。先求两个链表的长度
假设长链表是A 长度lenA 短链表B 长度LenB
长链表头节点开始走,并lenA-=1 当lenA==lenB的时候说明链表尾部对齐了,这样就开始直接按顺序比较链表节点值是否相等了。时间复杂度是O(M+N)
# Definition for singly-linked list. # class ListNode: # def __init__(self, x): # self.val = x # self.next = None class Solution: # @param headA: the first list # @param headB: the second list # @return: a ListNode def getIntersectionNode(self, headA, headB): # Write your code here if headA == None: return None if headB == None: return None lenA = self.getLength(headA) lenB = self.getLength(headB) A = None B = None if lenA > lenB: A = headA B = headB else: A = headB B = headA tmp = lenA lenA = lenB lenB = tmp while lenA>lenB: lenA -=1 A = A.next while A and B: if A.val == B.val: return A A = A.next B = B.next def getLength(self,head): length = 0 p = head while p!=None: p = p.next; length +=1 return length
总耗时: 340 ms.
/** * Definition for singly-linked list. * public class ListNode { * int val; * ListNode next; * ListNode(int x) { * val = x; * next = null; * } * } */ public class Solution { /** * @param headA: the first list * @param headB: the second list * @return: a ListNode */ public ListNode getIntersectionNode(ListNode headA, ListNode headB) { // Write your code here if(headA == null) return null; if(headB == null) return null; if(headA == headB ) return headA; // 求 A B的长度 int lenA = getLength(headA); int lenB = getLength(headB); ListNode A = null; ListNode B = null; // A是比较长的链表 if(lenA>lenB){ A = headA; B = headB; }else{ A = headB; B = headA; int tmp = lenA; lenA = lenB; lenB = tmp; } while(lenA>lenB){ A = A.next; lenA--; } while(A!=null && B!=null){ if(A.val == B.val){ return A; } A = A.next; B = B.next; } return null; } public int getLength(ListNode head){ int length = 0; ListNode p = head; while(p!=null){ length++; p = p.next; } return length; } }
总耗时: 2028 ms