剑指offer 面试题15: 链表中倒数第k个结点 题解
2016-04-16 17:40
561 查看
剑指offer 面试题15: 链表中倒数第k个结点
提交网址: http://www.nowcoder.com/practice/529d3ae5a407492994ad2a246518148a?tpId=13&tqId=11167
时间限制:1秒 空间限制:32768K
本题知识点:链表
分析:
刚看到此题时,会想到的办法是遍历两次,先用计数器获得链表长度,然后第二次遍历时走到n-k+1结点处即可,这样做时间复杂度为O(n+k);
如果要求只遍历一次,或 时间复杂度就为O(n),那就可以采用两个指针(先后指针,速度相同),pAhead先动,当pAhead到k-1时pBehind开始动,则当pAhead到尾部时,pBehind恰好到倒数第k个结点处。
另外需要注意一点,k是无符号整型的,而下标idx需要与k比较,也设为无符号整型比较好。
提交网址: http://www.nowcoder.com/practice/529d3ae5a407492994ad2a246518148a?tpId=13&tqId=11167
时间限制:1秒 空间限制:32768K
本题知识点:链表
分析:
刚看到此题时,会想到的办法是遍历两次,先用计数器获得链表长度,然后第二次遍历时走到n-k+1结点处即可,这样做时间复杂度为O(n+k);
如果要求只遍历一次,或 时间复杂度就为O(n),那就可以采用两个指针(先后指针,速度相同),pAhead先动,当pAhead到k-1时pBehind开始动,则当pAhead到尾部时,pBehind恰好到倒数第k个结点处。
另外需要注意一点,k是无符号整型的,而下标idx需要与k比较,也设为无符号整型比较好。
#include<iostream> using namespace std; struct ListNode { int val; struct ListNode *next; ListNode(int x) : val(x), next(NULL) { } }; class Solution{ public: ListNode* FindKthToTail(ListNode* pListHead, unsigned int k) { if(pListHead==NULL || k==0) return NULL; ListNode *pAhead,*pBehind; pAhead=pListHead; pBehind=NULL; for(unsigned int idx=0; idx<k-1;idx++) { if(pAhead->next==NULL) return NULL; else pAhead=pAhead->next; } pBehind=pListHead; while(pAhead->next != NULL) { pAhead=pAhead->next; pBehind=pBehind->next; } return pBehind; } }; // 以下为测试部分 /* int main() { ListNode *p_head,*kthNode; Solution sol; p_head=new ListNode(5); p_head->next=new ListNode(2); p_head->next->next=new ListNode(3); p_head->next->next->next=new ListNode(8); // p_head=NULL; // 空结点的情形,上面4个结点都注释掉。 kthNode=sol.FindKthToTail(p_head, 2); // 后面的2按测试需求调整 if(kthNode!=NULL) cout<<"The value of kth Node is: "<<kthNode->val<<endl; else cout<<"The Node does not exist."<<endl; return 0; } */