LeetCode 160.相交链表

题目

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

如下面的两个链表:

image

在结点c1开始相交

题目链接

示例

输入: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 个节点。

题目分析

借鉴官方题解评论区一位楼主的创意,这道题的算法我称之为“浪漫算法”——对的人总会相交。

所谓“浪漫算法”,就是用两个指针分别遍历两个链表。如果第一个指针遍历完,则让其指向headB;如果第二个指针遍历完,则让其指向headA;如果两个指针相等,则遍历结束,返回这个指针。

在这里简单验证一下方法有效性,令headA长度为m,headB长度为n,那么遍历次数最多为m+n。如果两个链表有相交的部分,按照上面的方法遍历,两个指针一定在同一个位置停止遍历。

举例说明:

listA = [4,1,8,4,5], listB = [5,0,1,8,4,5]

p1 = listA,p2 = listB

同时遍历p1和p2

  1. p1 = 4, p2 = 5
  2. p1 = 1, p2 = 0
  3. p1 = 8, p2 = 1
  4. p1 = 4, p2 = 8
  5. p1 = 5, p2 = 4
  6. p1 = listB = 5, p2 = 5
  7. p1 = 0, p2 = listA = 4
  8. p1 = 1, p2 = 1
  9. p1 = 8, p2 = 8,相遇了
typedef struct ListNode* list;
struct ListNode *getIntersectionNode(struct ListNode *headA, struct ListNode *headB) {
    if (headB == NULL || headA == NULL) return 0;

    list p1, p2;
    p1 = headA;
    p2 = headB;

    while (p1 != p2){
        if (p1 == NULL){
            p1 = headB;
        }else {
            p1 = p1->next;
        }
        if (p2 == NULL){
            p2 = headA;
        }else {
            p2 = p2->next;
        }
    }

    if (p1 == NULL) return 0;
    else return p1;
}

你可能感兴趣的:(LeetCode 160.相交链表)