给一个链表,若其中包含环,请找出该链表的环的入口结点,否则,输出null。


 

如果有环, 环的数目设为n,则先让p1,p2都指向头结点,p1先向前走n步,可以发现p1,领先p2指针n步,当p2走到环口时,则p1刚走完环,与p2相遇,按照此思路求解即可

public class Test {

    //找到一快一满指针相遇处的节点,相遇的节点一定是在环中

    public static ListNode meetingNode(ListNode head) {

        if(head==null)

            return null;

         

        ListNode slow = head.next;

        if(slow==null)

            return null;

         

        ListNode fast = slow.next;

        while (slow != null && fast != null) {

            if(slow==fast){

                return fast;

            }

            slow=slow.next;

            fast=fast.next;

             

            if(fast!=slow){

                fast=fast.next;

            }

        }

        return null;

    }

    public ListNode EntryNodeOfLoop(ListNode pHead) {

        ListNode meetingNode=meetingNode(pHead);

        if(meetingNode==null)

            return null;

//      得到环中的节点个数

        int nodesInLoop=1;

        ListNode p1=meetingNode;

        while(p1.next!=meetingNode){

            p1=p1.next;

            ++nodesInLoop;

        }

//      移动p1

        p1=pHead;

        for(int i=0;i<nodesInLoop;i++){

            p1=p1.next;

        }

//      移动p1,p2

        ListNode p2=pHead;

        while(p1!=p2){

            p1=p1.next;

            p2=p2.next;

        }

        return p1;

    }

}

猜你喜欢

转载自blog.csdn.net/qq_32459653/article/details/81135145