zoukankan      html  css  js  c++  java
  • 【剑指Offer】面试题52. 两个链表的第一个公共节点

    题目

    输入两个链表,找出它们的第一个公共节点。

    如下面的两个链表:

    在节点 c1 开始相交。

    示例 1:

    输入:intersectVal = 8, listA = [4,1,8,4,5], listB = [5,0,1,8,4,5], skipA = 2, skipB = 3
    输出:Reference of the node with value = 8
    输入解释:相交节点的值为 8 (注意,如果两个列表相交则不能为 0)。从各自的表头开始算起,链表 A 为 [4,1,8,4,5],链表 B 为 [5,0,1,8,4,5]。在 A 中,相交节点前有 2 个节点;在 B 中,相交节点前有 3 个节点。
    

    示例 2:

    输入:intersectVal = 2, listA = [0,9,1,2,4], listB = [3,2,4], skipA = 3, skipB = 1
    输出:Reference of the node with value = 2
    输入解释:相交节点的值为 2 (注意,如果两个列表相交则不能为 0)。从各自的表头开始算起,链表 A 为 [0,9,1,2,4],链表 B 为 [3,2,4]。在 A 中,相交节点前有 3 个节点;在 B 中,相交节点前有 1 个节点。
    

    示例 3:

    输入:intersectVal = 0, listA = [2,6,4], listB = [1,5], skipA = 3, skipB = 2
    输出:null
    输入解释:从各自的表头开始算起,链表 A 为 [2,6,4],链表 B 为 [1,5]。由于这两个链表不相交,所以 intersectVal 必须为 0,而 skipA 和 skipB 可以是任意值。
    解释:这两个链表不相交,因此返回 null。
    

    注意:

    • 如果两个链表没有交点,返回 null.
    • 在返回结果后,两个链表仍须保持原有的结构。
    • 可假定整个链表结构中没有循环。
    • 程序尽量满足 O(n) 时间复杂度,且仅用 O(1) 内存。

    本题同【LeetCode】160. 相交链表

    思路一:链表拼接

    通过链表拼接消除差值,如果一个链表先走到尾部,则指向另一个链表。

    代码

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

    class Solution {
    public:
        ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) {
            if (!headA || !headB){
                return nullptr;
            }
            ListNode *pA = headA, *pB = headB;
            while (pA != pB) {
                pA = pA == nullptr ? headB : pA->next;
                pB = pB == nullptr ? headA : pB->next;
            }
            return pA;
        }
    }
    

    思路二:双指针

    如果链表相交,则链表公共节点都在尾部。

    1. 先计算两个链表长度。
    2. 让长链表指针先走多出长度,然后两个链表同时走,如果相遇则为相交节点。

    代码

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

    class Solution {
    public:
        ListNode *getIntersectionNode(ListNode *headA, ListNode *headB) {
            if (!headA || !headB) return nullptr;
            int len1 = len(headA), len2 = len(headB);        
            if (len1 >= len2) {
                int move = len1 - len2;
                while (move--) {
                    headA = headA->next;                
                }     
            } else {
                int move = len2 - len1;
                while (move--) {
                    headB = headB->next;
                }
            }
            while (headA != headB) {            
                headA = headA->next;
                headB = headB->next;
            }
            return headA;
        }
    
        int len(ListNode *head) {
            int len = 0;
            while (head) {
                ++len;
                head = head->next;
            }
            return len;
        }
    };
    
  • 相关阅读:
    Codeforces Gym 100571A A. Cursed Query 离线
    codeforces Gym 100500 J. Bye Bye Russia
    codeforces Gym 100500H H. ICPC Quest 水题
    codeforces Gym 100500H A. Potion of Immortality 简单DP
    Codeforces Gym 100500F Problem F. Door Lock 二分
    codeforces Gym 100500C D.Hall of Fame 排序
    spring data jpa 创建方法名进行简单查询
    Spring集成JPA提示Not an managed type
    hibernate配置文件中的catalog属性
    SonarLint插件的安装与使用
  • 原文地址:https://www.cnblogs.com/galaxy-hao/p/12348024.html
Copyright © 2011-2022 走看看