1. 程式人生 > >如何判斷一個單鏈表是否有環?

如何判斷一個單鏈表是否有環?

算法 查找

public class LinkedListRing{

static class LinkedNode<T>{

private T t ;

private LinkedNode<T> next = null;

public LinkedNode(T t) {

this.t=t;

}

public LinkedNode<T> getNext() {

return next;

}

public void setNext(LinkedNode<T> next) {

this.next = next;

}

public String toString(){

return String.valueOf(t) ;

}

}

public static void main(String[] args) {

/**

* 造一個有環鏈表

*/

LinkedNode<String> l = new LinkedNode<String>("!");

LinkedNode<String> node = null;

LinkedNode<String> last = l;

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

LinkedNode<String> temp = new LinkedNode<String>(i+"");

last.setNext(temp);

last = temp;

if(i==2){

node = temp;

}

if(i==4){

temp.setNext(node);

}

}

/**

* 尋找環入口

*/

System.out.println(findSingleLinkedRing(l));

}

/**

如何判斷一個單鏈表是否有環?

有環返回進入環的第一個節點,無環返回空

時間復雜度O(N),額外空間復雜度O(1)

*

*

*/

public static LinkedNode<String> findSingleLinkedRing(LinkedNode<String> l){

LinkedNode<String> index1 = l;

LinkedNode<String> index2 = l;

try{

while(true){

/**

* 慢指針

*/

index1 = index1.getNext();

/**

* 快指針

* 無環會出java.lang.NullPointerException

*/

index2 = index2.getNext().getNext();

/**

* 無重復則不存在環點

*/

if(index1==null || index2 == null){

return null;

}

/**

* 有重復則將快指針從頭單位步長執行,慢指針從之前重復位置執行

*

*/

if(index1 == index2){

index2 = l;

while(true){

index1 = index1.getNext();

index2 = index2.getNext();

/**

* 再次重合位置為入環位置

*/

if(index1 == index2){

return index1;

}

}

}

}

}catch(NullPointerException e){

return null;

}

}

}


如何判斷一個單鏈表是否有環?