题目
思路1
假设整个链表有N个结点,那么倒数第K个结点就是从头结点开始的第n-k-1
个结点。只要从头结点开始往后走n-k+1
步就可以了。得到结点总数只需从头开始遍历链表,没经过一个结点,计数器加1就行了。也就是说需要遍历链表两次,第一次统计出链表中结点的个数,第二次就能找到倒数第k个结点。
思路2
只遍历链表一次就能找到倒数第k个结点,需要定义两个指针,第一个指针从链表的头指针开始遍历向前走k-1
。第二个指针保持不动;从第k步开始,第二个指针也开始从链表的头指针开始遍历。由于两个指针的距离保持在k-1
,当第一个(走在前面的)指针到达链表的尾指结点时,第二个指针正好是倒数第k个结点。
package com.zhumq.leetcode;
public class KthNodeFromEnd {
/**
* 输入一个链表,输出该链表中倒数第k哥结点。
* 为了符合大多数人的习惯,本题从1开始计数,即链表的尾结点是倒数第1个结点。
* 例如一个链表有6个结点,从头结点开始它们的值依次是1,2,3,4,5,6.这个链表的倒数第3个结点是值为4的结点
*/
/**
* 注意特殊的测试用例:
* 测试用例;功能测试(第k个结点在链表的中间,第k个结点在链表的头结点,第k个结点在链表的尾结点)
* 特殊输入测试:链表的头结点为Null指针,链表的头结点综述少于k,k等于0
*/
public ListNode FindKthToTail(ListNode head,int k){
if(head == null || k <= 0){
return null;
}
ListNode ANode = head;
ListNode BNode = null;
//A指针先向前走k-1步
for(int i = 0;i<k-1;i++){
if(ANode.next != null)
ANode = ANode.next;
else
return null;
}
BNode = head;
while(ANode.next != null){
ANode = ANode.next;
BNode = BNode.next;
}
return BNode;
}
public class ListNode{
public int val;
public ListNode next;
public ListNode(int val) {
this.val = val;
next = null;
}
}
}