判断一个有环链表的入口节点

来源:互联网 发布:虚拟机linux ip地址 编辑:程序博客网 时间:2024/06/07 08:40

思路:类似于求链表的倒数第K的节点,使用两个指针p1,p2。使p2先向后移动环的长度个节点,然后两个指针一起向后移动,当p1移动到入口时,p2也移动到入口。如何求出环的长度呢?从判断两个链表有环这个问题中我们可以得到链表环中一个节点,从此节点出发当再次回到此节点时,即得到长度。

/** * Created by lrx on 2017/4/4. */class ListNode {    int val;    ListNode next = null;    ListNode(int val) {        this.val = val;    }}// 找到有环链表的入口节点public class EntryNodeOfLoop {    private static int getLength(ListNode head) {        ListNode p1,p2;        // 先各自走一下        p1 = head.next;        if (p1 != null)            p2 = p1.next;        else {            return -1;        }        while(p2 != null && p1.val != p2.val) {            p1 = p1.next;            if (p2.next != null)                p2 = p2.next.next;            else            p2 = null;        }        if (p2 == null) return -1;        int length = 1;        p2 = p2.next;        while (p2.val != p1.val) {            p2 = p2.next;            length++;        }        return length;    }    public static ListNode entryNodeOfLoop(ListNode pHead)    {        if (pHead == null) return null;        int length = getLength(pHead);        // 无环链表        if (length == -1) return null;        ListNode p1 = pHead,p2 = pHead;        // p2先向后移动环的长度        for (int i=0; i<length; i++) {            p2 = p2.next;        }        while(p1.val != p2.val) {            p1 = p1.next;            p2 = p2.next;        }        return p1;    }    public static void main(String[] args) {        entryNodeOfLoop(new ListNode(1));    }}
0 0
原创粉丝点击