#剑指offer36两个链表的第一个公共结点

两个链表的第一个公共结点

https://www.nowcoder.com/practice/6ab1d9a29e88450685099d45c9e31e46?tpId=13&&tqId=11189&rp=1&ru=/ta/coding-interviews&qru=/ta/coding-interviews/question-ranking

剑指offer36两个链表的第一个公共结点

剑指offer36
其他博客解读参考
1、直接双重循环比较
个人答案

//直接两重循环比较
    ListNode* FindFirstCommonNode( ListNode* pHead1, ListNode* pHead2) {
        ListNode* temp=pHead2;
        while(pHead1)
        {
            pHead2=temp;
            while(pHead2)
            {
                if(pHead1==pHead2)
                    return pHead1;
                 pHead2=pHead2->next;
            }
            pHead1=pHead1->next;
        }
        return nullptr;
    }

2、差值法(较长优先走):两个链表在公共节点之前长度不一定一致,所以不能同时遍历比较。可以让长的先走n-m步,然后再同时走,进行比较
个人答案

//双指针法1:两个链表在公共节点之前长度不一定一致,所以不能同时遍历比较。
//          可以让长的先走n-m步,然后再同时走,进行比较
    ListNode* FindFirstCommonNode( ListNode* pHead1, ListNode* pHead2) {
        int n=0;
        int m=0;
        ListNode* head1=pHead1;
        ListNode* head2=pHead2;
        while(pHead1)
        {
            ++n;
            pHead1=pHead1->next;
        }
         while(pHead2)
        {
            ++m;
            pHead2=pHead2->next;
        }
        if(n>m)
        {
            int x=n-m;
            while(x--)
            {
                head1=head1->next;
            }
        }
        else if(m>n)
        {
            int x=m-n;
            while(x--)
            {
                head2=head2->next;
            }
        }
        while(head1&&head2)
        {
            if(head1==head2)
                return head1;
            head1=head1->next;
            head2=head2->next;
        }
        return nullptr;
    }

2、双指针法
个人答案
两个链表公共的前缀部分可能不一致,可以使用差值法,长的提前走完差值长度,但需要多次遍历.
也可以将两个链表接在一起长度均为m+n,即相当于两个链表分别加上对方链表作为自己的前缀,从而使得,两链表公共部分之前的前缀长度一致,可以同时走到公共部分。
注意:
1、若两链表长度一致,在附加前缀部分就可以找出公共点(无论有无公共点)
2、a+b之后,两个链表长度一致,所以有公共节点,返回公共节点,遍历次数<=m+n;无公共节点,尾部nullptr也可以看作虚拟的公共节点,返回虚拟公共节点nullptr,遍历m+n+1次

class Solution {
public:
//双指针法:两个链表公共的前缀部分可能不一致,可以使用差值法,长的提前走完差值长度,
//         但需要多次遍历.
//         也可以将两个链表接在一起长度均为m+n,即相当于两个链表分别加上对方链表作为自己的前缀
//         从而使得,两链表公共部分之前的前缀长度一致,可以同时走到公共部分。
//注意:1、若两链表长度一致,在附加前缀部分就可以找出公共点(无论有无公共点)
//     2、a+b之后,两个链表长度一致,所以有公共节点,返回公共节点,遍历次数<=m+n;
//        无公共节点,尾部nullptr也可以看作虚拟的公共节点,返回虚拟公共节点nullptr,遍历m+n+1次
    ListNode* FindFirstCommonNode( ListNode* pHead1, ListNode* pHead2) {
        ListNode* head1=pHead1;
        ListNode* head2=pHead2;
        while(head1!=head2)
        {
            head1=head1?head1->next:pHead2;//head1==null时,换上另一个链表
            head2=head2?head2->next:pHead1;
        }
        return head1;
    }
};
全部评论

相关推荐

听说改名字就能收到offer哈:Radis写错了兄弟
点赞 评论 收藏
分享
11-29 11:21
门头沟学院 Java
总包48.5w,意想不到的价格
想开了的垂耳兔很喜欢拱白菜:转人工
点赞 评论 收藏
分享
评论
点赞
收藏
分享
牛客网
牛客企业服务