(链表)求相交链表交点

1.问题描述:

编写一个程序,找到两个单链表相交的起始节点。

如下面的两个链表:

在节点 c1 开始相交。

2.使用双指针解决该题

2.1 思路与图解

若相交,链表A: a+c, 链表B : b+c. a+c+b+c = b+c+a+c 。则会在公共处c起点相遇。若不相交,a +b = b+a 。因此相遇处是NULL

2.2 代码实现:

public ListNode getIntersectionNode(ListNode headA, ListNode headB) {
        if(headA == null || headB == null) return null;
        ListNode pA = headA, pB = headB;
        // 在这里第一轮体现在pA和pB第一次到达尾部会移向另一链表的表头, 而第二轮体现在如果pA或pB相交就返回交点, 不相交最后就是null==null
        while(pA != pB) {
            pA = pA == null ? headB : pA.next;
//三目运算
//表达式1 ? 表达式2:表达式3;
//表达式1必须是一个条件表达式或者返回值必须为boolean类型的。表达式2和表达式3则没有什么要求。
//当表达式1的返回值为true时,返回表达式2的值。否则,返回表达式3的值。
//当pA==null时,PA=headB,也就是B链表的头结点;当PA!=null 时,PA=PA.next
pB
= pB == null ? headA : pB.next; } return pA; }

 2.3 复杂度分析

   时间复杂度 : O(m+n)

   空间复杂度 : O(1)

3.使用哈希表解题

3.1 思路:遍历链表 A 并将每个结点的地址/引用存储在哈希表中。然后检查链表 B 中的每一个结点 bi是否在哈希表中。若在,则 bi为相交结点

3.2 代码实现

public class Solution {
    public ListNode getIntersectionNode(ListNode headA, ListNode headB) {
        Set s = new HashSet();
        ListNode p = headA;
        ListNode q = headB;
        //定义一个set之后,不断遍历p链表,然后将所有元素加入到set中
        while(p!=null) {
            s.add(p);
            p = p.next;
        }
        while(q!=null) {
            //遍历q链表,如果q链表的元素出现在set中,
            //重合,而这个重合的就是第一个相交的节点就说明
            //p和q两个链表有
            if(s.contains(q)) {
                return q;
            }
            q = q.next;
        }
        return null;
    }
}

3.3复杂度分析

时间复杂度 : O(m+n)。
空间复杂度 : O(m) 或 O(n)。

原文地址:https://www.cnblogs.com/yangzhixue/p/12263257.html