題目:
輸入一個單向鏈表。如果該鏈表的結點數爲奇數,輸出中間的結點;如果鏈表結點數爲偶數,輸出中間兩個結點前面的一個。
思考:
最簡單的解法:從頭到尾遍歷一遍數組,得到鏈表大小n。然後再從頭走n/2次,則一共需要的時間爲1.5n。
優化:想起以前一道題目,用n的方法反轉一個單向鏈表。如果只用一個變量header,是不可能的,用了preHeader,proHeader,nowHeader三個變量則變成了一種可能。那就想一想有沒有空間換時間的可能性。假如一開始我用兩個變量,firstHeader,secHeader,題目要求的輸出結點總是結點總和的一半,那我可不可以first和sec一起走,但是每次都是sec走兩下first走一下,當sec到達末尾後,first剛好走了一半。通過多了一個變量,來節約了0.5n次的時間。
代碼:
struct Node{
int key;
Node* next;
};
class List{
public:
List():header(NULL){
}
Node* findNode(){
if (header==NULL)
{
return;
}
Node* first = header;
Node* sec =header;
int walkCount = 0;
while (sec!=NULL)
{
sec = sec->next;
walkCount++;
if (walkCount%2==0 && sec!=NULL)
{
first = first->next;
}
}
return first;
}
Node* header;
};