鍊錶 相交結點與環問題

2021-09-06 12:02:16 字數 2855 閱讀 9143

基本問題:

1.兩個鍊錶中的第乙個公共結點

[解題思路]

a.先求得兩個鍊錶的長度,得到鍊錶長度差d

b.根據鍊錶長度差,首先讓長鍊錶的指標先走d-1步,之後兩個指標一起走,發現相同結點時就是公共結點

int len1 = 0, len2 = 0;

listnode p1 = head1, p2 =head2;

while (p1 != null

)

while (p2 != null

)

listnode listlong = null, listshort = null

;

int lendiff = 0;

if(len1 >len2)

else

for(int i = 0; i < lendiff; i++)

while(listlong != null && listshort != null && (listlong !=listshort))

return listlong;

2.如何判斷乙個鍊錶中是否存在環

[解題思路]

和上題類似,維護兩個指標,乙個指標每次走1步,另乙個指標每次走2步,如果快指標追上了慢指標,則鍊錶中存在環

1

public

static

boolean

checkcircle2(listnode head)

56 listnode fast = head, slow =head;

7while (fast != null && fast.next != null

) 13}14

return !(fast == null || fast.next == null

);15 }

擴充套件問題:

1.求問題2中環的入口點

如明確知曉鍊錶中存在環,則在環中將鍊錶拆開,則就變成上面的問題1,找到入口結點之後恢復鍊錶

1

public

static

listnode findportal(listnode head)

56 listnode fast = head, slow =head;

7 listnode head2 = null, tail = null;8

while (fast != null && fast.next != null

) 18}19

20 listnode result =findcommonnode(head, head2);

21 tail.next =head2;

2223

return

result;24}

2526

private

static

listnode findcommonnode(listnode head1, listnode head2)

30int len1 = 0, len2 = 0;

31 listnode p1 = head1, p2 =head2;

32while (p1 != null

) 36

37while (p2 != null

) 41

42 listnode listlong = null, listshort = null;43

int lendiff = 0;

44if(len1 >len2) else

5354

for(int i = 0; i < lendiff; i++)

5758

while(listlong != null && listshort != null && (listlong !=listshort))

6263

return

listlong;

64 }

這題還有另外的解題思路:

假設兩個指標相遇時slow指標走了s步,則fast指標走了2s步(因為慢指標走一步,快指標走兩步)

此時fast指標可能繞環走了n圈(n >= 0), 則有2s = s + nr; ==> s = nr;

設煉表起點到環的入口點距離為a,環入口點到兩指標相遇點距離為x.==>s = a + x;

==>a + x = nr;

==>a + x = (n-1)r + r

==>a + x = (n-1)r + l - a

==>a = (n-1)r + l - x -a;

則我們在發現fast指標和slow指標相遇時,另外使用兩個指標,分別指向煉表頭結點和相遇結點,同時開始走,則他們相遇結點就是

環的入口結點

1

public

static

listnode findportal2(listnode head)

56 listnode fast = head, slow =head;

7while(fast != null && fast.next != null)13

}1415if(fast == null || fast.next == null)18

19 listnode p =head;

20while(p !=fast)

24return

p;25 }

鍊錶其他問題:

1.求鍊錶倒數第k個結點

2.求鍊錶的中間結點,如鍊表中結點總數為奇數,返回中間結點;如為偶數,返回中間兩個結點的任意乙個

判斷鍊錶相交 環

程式設計判斷倆個鍊錶是否相交 給出倆個單向鍊錶的頭指標,比如h1,h2,判斷這倆個鍊錶是否相交。為了簡化問題,我們假設倆個鍊錶均不帶環。問題擴充套件 1.如果鍊錶可能有環列?2.如果需要求出倆個鍊錶相交的第乙個節點列?以下是演算法實現部分 如何判斷乙個單鏈表是有環的?注意不能用標誌位,最多只能用兩個...

鍊錶相交問題

1 判斷兩個鍊錶是否相交 假設兩個鍊錶均不帶環 有四種方法 解法1 直觀的想法 判斷第乙個鍊錶的每個節點是否在第二個鍊錶中,這種方法的時間複雜度為o length h1 length h2 解法2 利用計數的方法 對第乙個鍊錶的節點位址進行hash排序,建立hash表,然後針對第二個鍊錶的每個節點的...

鍊錶相交問題

問題描述 給定兩鍊錶的頭結點,判斷兩鍊錶是否存在公共部分 相交 若相交返回相交的第乙個節點。經分析發現該問題可以分成如下兩個子問題進行解決。子問題一 兩無環鏈表是否相交 演算法一 假設list1長度為l1,list2長度為l2,假設公共部分長為m,由l1 l2 m l2 l1 m可知第一路先遍歷li...