链表相交问题
链表
链表相交问题
思路来源
一周刷爆LeetCode,算法大神左神(左程云)耗时100天打造算法与数据结构基础到
笔记内容
-
问题描述:
现有两个单向链表,需要判断两个链表是否相交,若相交,返回链表最开始的交点,若不相交,则返回null
-
算法思路:
-
首先需要判断两个链表是否是环形链表,并获取环形链表的环开始点
-
针对两个链表的不同情况进行分析:
-
若两个链表都不存在环,那么两个链表要么从头至尾都没有相交节点,要么从相交节点开始到结尾都是共用的;
-
若两个链表中存在一个环,那么两个链表不相交;
-
若两个链表都存在环,那么需要根据环开始点进行判断。如果是同一个开始点,那么两个链表必相交,相交点可能在该点前,视作第一种情况处理;如果开始点不同,相交点可能在环内或者不相交。
-
-
-
代码实现
class ListNode { int val; ListNode next; ListNode() {} ListNode(int val) { this.val = val; } ListNode(int val, ListNode next) { this.val = val; this.next = next; } } public static ListNode isMeet(ListNode head1,ListNode head2){ ListNode loop1 = hasCycle(head1); ListNode loop2 = hasCycle(head2); if(loop2 == null && loop1 == null){ //两个无环 int p = length(head1,null)-length(head2,null); loop1 = p > 0 ? head1 : head2 ; loop2 = loop1 == head1 ? head2 : head1; p = Math.abs(p); while (p>0){ loop1 = loop1.next; p--; } while (loop2 != null && loop1 != null){ if(loop2 == loop1){ return loop1; } loop1 = loop1.next; loop2 = loop2.next; } }else if(loop2 == null || loop1 == null){ //存在一个有环 return null; }else { //两个环 if(loop2 == loop1){ int p = length(head1,loop1)-length(head2,loop2); loop1 = p > 0 ? head1 : head2 ; loop2 = loop1 == head1 ? head2 : head1; p = Math.abs(p); while (p>0){ loop1 = loop1.next; p--; } while (loop2 != null && loop1 != null){ if(loop2 == loop1){ return loop1; } loop1 = loop1.next; loop2 = loop2.next; } }else { ListNode cur = loop1.next; while (cur != loop1){ if(cur == loop2){ return loop1; } cur = cur.next; } } } return null; } public static int length(ListNode head,ListNode end){ int count = 0; if(end == null){ while (head != null){ count++; head = head.next; } }else { while (head != end){ count++; head = head.next; } } return count; } //快慢指针 public static ListNode hasCycle(ListNode head) { if(head == null || head.next == null || head.next.next == null){ return null; } ListNode slow = head.next; ListNode fast = head.next.next; while (slow != fast){ if(fast.next == null || fast.next.next == null){return null;} slow = slow.next; fast = fast.next.next; } fast = head; while (slow != fast){ fast = fast.next; slow = slow.next; } return fast; }
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 别再用vector<bool>了!Google高级工程师:这可能是STL最大的设计失误
· 单元测试从入门到精通
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理
· 上周热点回顾(3.3-3.9)