題目:輸入一個鏈表,輸出該鏈表中倒數第K個節點。爲了符合大多數人的習慣,本題從1開始計數,即鏈表的尾節點是倒數第1個節點。例如一個鏈表有6個節點,從頭節點開始他們的值依次爲1,2,3,4,5,6.這個鏈表的倒數第三個節點是值爲4的節點。node
分析:不能屢次遍歷鏈表,只能一次遍歷。ios
/* 劍指offer面試題15 */ #include <iostream> using namespace std; struct ListNode{ ListNode* Next; int data; }; /* 把題目看錯,當作刪除了。可是刪除功能能夠實現, 一樣存在和題目同樣的問題,存在屢次遍歷問題。 爲了代碼質量更好要求只遍歷一次。 */ ListNode* DeleteKnode(ListNode** head,int k){ if(*head == NULL || k <= 0){ return NULL; } ListNode* p = *head; ListNode* q = new ListNode; int count = 0; int num = 0; while(p != NULL){ p = p->Next; count++; } //加入k大於鏈表長度,非法 if(k > count){ return NULL; } //刪除尾節點 if(k == 1){ p = *head; int i=1; while(i<(count-1)){ p = p->Next; i++; } q = p->Next; delete q; q = NULL; p->Next = NULL; return *head; } //刪除頭節點 if(k == count){ p = *head; q = p->Next; delete p; p = NULL; return q; } else{ p = *head; while(p != NULL && (count-k-1) > num){ num++; p = p->Next; } q = p->Next; p->Next = q->Next; delete q; q = NULL; } return p; } void Print(ListNode** head,int k){ if(*head == NULL || k <= 0){ return; } ListNode* first = *head; int length = 0; for(int i=0;i<k-1;++i){ if(first->Next != NULL){ //這是關鍵步驟!! first = first->Next; length++; } else{ return; } } ListNode* second = *head; while(first->Next != NULL){ first = first->Next; length++; second = second->Next; } cout << second->data << endl; } int main() { ListNode* head = new ListNode; ListNode* One = new ListNode; ListNode* Two = new ListNode; ListNode* tail = new ListNode; head->data = 0; head->Next = One; One->data = 1; One->Next = Two; Two->data = 2; Two->Next = tail; tail->data = 3; tail->Next = NULL; int k; cin >> k; /* ListNode* p = DeleteKnode(&head,k); while(p != NULL){ cout << p->data << " "; p = p->Next; } */ Print(&head,k); return 0; }