剑指offer-面试题15:链表中倒数第K个结点

来源:互联网 发布:手机可以注册淘宝店铺吗 编辑:程序博客网 时间:2024/05/16 07:17

题目:输入一个链表,输出该链表中倒数第K个结点。为了符合大多人的习惯,本题从1开始计数,即链表的尾结点是倒数第一个结点。例如一个链表有6个结点,从头结点开始它们的值依次是1、2、3、4、5、6.这个链表的倒数第三个结点是值为4的结点。

思路:这个题目我自己也实现了一遍,采用的方法是从头开始遍历链表,同时每次判断当前结点的后面第k-1个结点。如果后面的结点为NULL,则说明链表长度小于k,返回错误。如果不为空且尾结点不为空,那么往后遍历直到到达为结点,前面的那个结点即为要求的倒数第k个结点。但是这种方法每次都要求寻找后面第k-1个结点,比较麻烦。剑指offer这本书上提出了利用前后两个指针的方法,一个指针先从链表的头结点往后走k-1步,然后第二个指针指向表头,同时向链表后面移动,保持两个指针之间k-1个结点的距离,第一个指针指向尾结点的时候前面的指针即为倒数第K个结点,时间复杂度为O(n),注意链表为空和链表长度小于k的情况。

ListNode* FindKthToTail(ListNode* pListHead, int K){if(pListHead == NULL || K <= 0){cout << "Input is invalid!" << endl;return NULL;}ListNode* pAhead = pListHead;for(int i = 0; i < K - 1; ++i){pAhead = pAhead->m_pNext;if(pAhead == NULL){cout << "The list is short than K" << endl;return NULL;}} ListNode* pBehind = pListHead;while(pAhead->m_pNext != NULL){pAhead = pAhead->m_pNext;pBehind = pBehind->m_pNext;}return pBehind;}
举一反三:当我们用一个指针遍历链表不能解决问题的时候,可以尝试用两个指针来遍历链表,可以让其中一个指针遍历的速度快一些(比如一次在链表上走两步),或者让它先在链表上走若干步。

0 0