原題為某游戲公司試題,大意如下: 對於一個單向鏈表,試寫出找到它的倒序第m個元素(m >= 1)的函數,注意變量命名、注釋、時間復雜度、空間復雜度。注:要求寫出可編譯並可以運行通過的程序代碼。
這道題的常規做法或者說首先想到直覺的思路是先求得鏈表的長度,即元素總個數n,然後問題轉化為求順序第n-m+1個元素。但是由於這種方法要先計算長度,多了一次遍歷,效率不高,而且也不高內聚,因為依賴於求長度這個運算,而這個運算完全可獨立出來,為了盡量高內聚,減少對其它運算的依賴,需要進一步思考以求得更簡便高效的算法,其實可以這樣做,先求得順序第m個元素,用一指針P指向這個元素,用另一指針PR指向鏈表的頭部,現在好了,P和PR同時向右移動,直到P為空,則PR就是要求的倒序第m個元素,如果因m超越界限,則PR為空,表示沒找到,這樣一來,只需一次遍歷就夠了。C++代碼描述如下
1template<typename T>
2struct Node
3{
4 T data; /**////< 數據
5 Node* next; ///< 指向下一結點的指針
6} ;
7
8template<typename T>
9Node<T>* ReverseFind(Node<T>* head, size_t m)
10{
11 size_t n = 0;
12 Node<T> *p, *pR = NULL;
13 for (p = head;p;p = p->next)
14 {
15 if (++n == m)
16 {
17 pR = head;
18 continue;
19 }
20 if (pR)
21 {
22 pR = pR->next;
23 }
24 }
25 return pR;
26}