剑指offer(五十六)之链表中环的入口结点

题目描述

一个链表中包含环,请找出该链表的环的入口结点。

思路分析:

第一步,找环中相汇点。分别用p1,p2指向链表头部,p1每次走一步,p2每次走二步,直到p1==p2找到在环中的相汇点。

第二步,找环的入口。接上步,当p1==p2时,p2所经过节点数为2x,p1所经过节点数为x,设环中有n个节点,p2比p1多走一圈有2x=n+x; n=x;可以看出p1实际走了一个环的步数,再让p2指向链表头部,p1位置不变,p1,p2每次走一步直到p1==p2; 此时p1指向环的入口。

代码1:

<span style="color:#993399;">/*
 public class ListNode {
    int val;
    ListNode next = null;

    ListNode(int val) {
        this.val = val;
    }
}
*/
public class Solution {

    ListNode EntryNodeOfLoop(ListNode pHead){
        if(pHead == null || pHead.next == null)
            return null;
        ListNode p1 = pHead;
        ListNode p2 = pHead;
        while(p2 != null && p2.next != null ){
            p1 = p1.next;
            p2 = p2.next.next;
            if(p1 == p2){
                p2 = pHead;
                while(p1 != p2){
                    p1 = p1.next;
                    p2 = p2.next;
                }
                if(p1 == p2)
                    return p1;
            }
        }
        return null;
    }
}</span>

代码2:

import java.util.HashMap;
public class Solution {

    public ListNode EntryNodeOfLoop(ListNode pHead){
        ListNode node = pHead;

        HashMap<ListNode,Boolean> map = new HashMap<>();

        while(node!=null){
            if(map.containsKey(node)){
                return node;
            }else{
                map.put(node,true);
                node = node.next;
            }
        }

        return null;
    }
}
时间: 2024-08-09 05:00:44

剑指offer(五十六)之链表中环的入口结点的相关文章

《剑指offer》:[37]如何得到链表环的入口地址

题目:如何得到链表环的入口结点 方案:分两步走: 第一步:先要找到链表中的环,得到环的结点的个数.可以设置两个指针一个走的比较快,一个比较慢,那么如果链表中存在一个环,那么这两个指针一定会陷入这个环中,快的指针一定会遇到慢的指针,所以很快就能遇到.因为前面有详细讲过,这里不再多介绍,给一张图吧. 第二步:得到环的个数以后,我们照样可以设置两个指针.第一个指针先前进N(N为环中结点的个数)步,然后和第二个指针以相同的速度前进,当它们相遇时的结点就是链表中环的入口. 具体过程如下图所示: 具体实现代

剑指offer(四十三)之删除链表中重复的结点

题目描述 在一个排序的链表中,存在重复的结点,请删除该链表中重复的结点,重复的结点不保留,返回链表头指针. 例如,链表1->2->3->3->4->4->5 处理后为 1->2->5 代码1: import java.util.*; public class Solution { public ListNode deleteDuplication(ListNode pHead) { if(pHead == null) return null; //定义一个链

【剑指offer】十,反转链表

题目描述 输入一个链表,反转链表后,输出链表的所有元素. 分析:此题学过数据结构的应该会首先想到链表建立时所采用的头插法,即每一个新插入进来的点均插在链表头.代码如下: 1 /* 2 public class ListNode { 3 int val; 4 ListNode next = null; 5 6 ListNode(int val) { 7 this.val = val; 8 } 9 }*/ 10 public class Solution { 11 public ListNode R

剑指offer(五十八)之正则表达式匹配

题目描述 请实现一个函数用来匹配包括'.'和'*'的正则表达式.模式中的字符'.'表示任意一个字符,而'*'表示它前面的字符可以出现任意次(包含0次). 在本题中,匹配是指字符串的所有字符匹配整个模式.例如,字符串"aaa"与模式"a.a"和"ab*ac*a"匹配,但是与"aa.a"和"ab*a"均不匹配 代码: <span style="color:#000099;">pu

剑指offer(五十四)之字符流中第一个不重复的字符

题目描述 请实现一个函数用来找出字符流中第一个只出现一次的字符.例如,当从字符流中只读出前两个字符"go"时,第一个只出现一次的字符是"g".当从该字符流中读出前六个字符"google"时,第一个只出现一次的字符是"l". 输出描述: 如果当前字符流没有存在出现一次的字符,返回#字符. 思路: 使用一个HashMap来统计字符出现的次数,同时用一个ArrayList来记录输入流,每次返回第一个出现一次的字符都是在这个Array

剑指offer(五十九)之二叉搜索树的后序遍历序列

题目描述 输入一个整数数组,判断该数组是不是某二叉搜索树的后序遍历的结果.如果是则输出Yes,否则输出No.假设输入的数组的任意两个数字都互不相同. 思路分析:BST的后序序列的合法序列是,对于一个序列S,最后一个元素是x (也就是根),如果去掉最后一个元素的序列为T,那么T满足:T可以分成两段,前一段(左子树)小于x,后一段(右子树)大于x,且这两段(子树)都是合法的后序序列. public class Solution { public boolean VerifySquenceOfBST(

剑指offer(五十二)之对称的二叉树

题目描述 请实现一个函数,用来判断一颗二叉树是不是对称的.注意,如果一个二叉树同此二叉树的镜像是同样的,定义其为对称的. 代码: <span style="color:#000099;">/* public class TreeNode { int val = 0; TreeNode left = null; TreeNode right = null; public TreeNode(int val) { this.val = val; } } */ public cla

剑指offer(五十五)之表示数值的字符串

题目描述 请实现一个函数用来判断字符串是否表示数值(包括整数和小数).例如,字符串"+100","5e2","-123","3.1416"和"-1E-16"都表示数值. 但是"12e","1a3.14","1.2.3","+-5"和"12e+4.3"都不是. 代码1: public class Solutio

剑指offer(五十)之序列化二叉树

题目描述 请实现两个函数,分别用来序列化和反序列化二叉树 代码: <span style="color:#000099;">/* public class TreeNode { int val = 0; TreeNode left = null; TreeNode right = null; public TreeNode(int val) { this.val = val; } } */ public class Solution { public int index =