剑指offer系列之十三:链表中的倒数第k个节点

题目描述

输入一个链表,输出该链表中倒数第k个结点。

举一个简单的例子,比如链表{1,2,3,4,5},如果要返回倒数第二个节点,也就是k=2,就相当于正数第5-k+1=4个节点,所以我们可以采用两次循环:一次循环得到链表的结点个数;另一次循环则是从链表中找到第n-k+1个节点。虽然是两次循环,但时间复杂度是O(n),需要注意的是,这里仍然需要对链表的边界条件进行判断。基于这种思路写出如下代码:

public ListNode FindKthToTail(ListNode head,int k) {
        if(head == null || k <= 0) return null;
        int nodesNum = 1;
        ListNode node = head;
        while(node.next != null){
            nodesNum++;
            node = node.next;
        }
        int i = 1;
        node = head;
        while(k <= nodesNum && i != nodesNum - k + 1){
            i++;
            node = node.next;
        }
        if(k <= nodesNum)
            return node;
        return null;
    }

还有一种思路就是创建两个指针,一个指针先走k-1部,当第k部的时候,另一个指针从第一个节点开始走,这样,第一个指针到达最后一个指针的时候,第二个指针刚好到达倒数第k个节点的位置。实现代码如下(已被牛客AC):

public ListNode FindKthToTail2(ListNode head,int k) {
        if(head == null || k <= 0) return null;
        ListNode pre = head;
        ListNode behind = null;
        for (int i = 0; i < k - 1; i++) {
            if(pre.next != null){
                pre = pre.next;
            }else {
                return null;
            }
        }

        behind = head;
        while(pre.next != null){
            pre = pre.next;
            behind = behind.next;
        }
        return behind;
    }
时间: 2024-09-14 08:54:32

剑指offer系列之十三:链表中的倒数第k个节点的相关文章

剑指offer系列之六十一:二叉树搜索树的第k个节点

题目描述 给定一颗二叉搜索树,请找出其中的第k大的结点.例如, 5 / \ 3 7 /\ /\ 2 4 6 8 中,按结点数值大小顺序第三个结点的值为4. 因为二叉搜索树是排序的,所以如果需要找出第k个节点只需要进行中序遍历就可以得到第k节点.不过中序遍历的结果就是排序的,所以实质上就是插入排序.可以利用一个集合,在遍历的过程中利用插入排序的算法就能得到第k个节点.下面是这种实现思路的实现代码(已被牛客AC): public class Solution { //采用非递归中序遍历的方式得到第k

剑指offer系列之五十三:字符流中第一个不重复的字符

题目描述 请实现一个函数用来找出字符流中第一个只出现一次的字符.例如,当从字符流中只读出前两个字符"go"时,第一个只出现一次的字符是"g".当从该字符流中读出前六个字符"google"时,第一个只出现一次的字符是"l". 输出描述: 如果当前字符流没有存在出现一次的字符,返回#字符. 这题与前面的第一个不重复的字符有些重复了,所以直接看代码(已被牛客AC): package com.rhwayfun.offer; impor

剑指offer系列之四十三:扑克牌顺子

题目描述 LL今天心情特别好,因为他去买了一副扑克牌,发现里面居然有2个大王,2个小王(一副牌原本是54张^_^)-他随机从中抽出了5张牌,想测测自己的手气,看看能不能抽到顺子,如果抽到的话,他决定去买体育彩票,嘿嘿!!"红心A,黑桃3,小王,大王,方片5","Oh My God!"不是顺子-..LL不高兴了,他想了想,决定大\小 王可以看成任何数字,并且A看作1,J为11,Q为12,K为13.上面的5张牌就可以变成"1,2,3,4,5"(大小王

剑指offer系列之三十三:第一个只出现一次的字符

题目描述 在一个字符串(1<=字符串长度<=10000,全部由字母组成)中找到第一个只出现一次的字符的位置.若为空串,返回-1.位置索引从0开始 第一个只出现一次的字符是关键,就意味着需要所有的字符进行出现次数的统计,所以我们需要两次遍历:第一次获取每个字符出现的次数:第二次把第一个只出现一次的字符找到.在Java中可以通过HashMap实现对每个字符次数的统计,由于在题目中并没有我们限定使用Java提供的内置结构,所以可以通过这种办法迅速找到第一个只出现一次的字符. 下面是基于这种思路的实现

剑指offer系列之六十三:滑动窗口的最大值

题目描述 给定一个数组和滑动窗口的大小,找出所有滑动窗口里数值的最大值.例如,如果输入数组{2,3,4,2,6,2,5,1}及滑动窗口的大小3,那么一共存在6个滑动窗口,他们的最大值分别为{4,4,6,6,6,5}: 针对数组{2,3,4,2,6,2,5,1}的滑动窗口有以下6个: {[2,3,4],2,6,2,5,1}, {2,[3,4,2],6,2,5,1}, {2,3,[4,2,6],2,5,1}, {2,3,4,[2,6,2],5,1}, {2,3,4,2,[6,2,5],1}, {2,

剑指offer系列之三:在二维数组中查找元素

题目描述: 在一个二维数组中,每一行都按照从左到右递增的顺序排序,每一列都按照从上到下递增的顺序排序.请完成一个函数,输入这样的一个二维数组和一个整数,判断数组中是否含有该整数. 由于题目条件的成立,所以使得这道题可以使用对角线的方法完成,可以从右上角的元素考虑,如果目标查找元素小于右上角的元素,那么不可能在右上角元素所在的列,如果目标大于剩余列的右上角的元素,那么不可能在该右上角元素所在的行.依照这个规律,就可以完成目标元素的查找(参考剑指offer书中的思路).基于此,我写出如下的代码(已被

[剑指Offer]5.二维数组中的查找

题目 在一个二维数组中,每一行都按照从左到右递增的顺序排序,每一列都按照从上到下递增的顺序排序.请完成一个函数,输入这样的一个二维数组和一个整数,判断数组中是否含有该整数. 思路 [算法系列之三十三]杨氏矩阵 代码 /*--------------------------------------- * 日期:2015-07-19 * 作者:SJF0115 * 题目: 5.二维数组中的查找 * 网址:http://www.nowcoder.com/books/coding-interviews/a

剑指offer系列之二十六:输出字符串的全排列

题目描述 输入一个字符串,按字典序打印出该字符串中字符的所有排列.例如输入字符串abc,则打印出由字符a,b,c所能排列出来的所有字符串abc,acb,bac,bca,cab和cba. 结果请按字母顺序输出. 输入描述: 输入一个字符串,长度不超过9(可能有字符重复),字符只包括大小写字母. 此题与剑指offer原题存在一些初入,在原题中并没有规定字符串中字符是否有重复的出现.不过思路是一致的,只不过是添加额外的判断罢了.下面说说我的思路吧:先不考虑是否出现重读字符,要对一个字符进行全排列,可以

剑指offer系列之十二:调整数组顺序使奇数位于偶数前面

题目描述 输入一个整数数组,实现一个函数来调整该数组中数字的顺序,使得所有的奇数位于数组的前半部分,所有的偶数位于位于数组的后半部分,并保证奇数和奇数,偶数和偶数之间的相对位置不变. 这道题第一思路自然是这样的:从头开始遍历这个数组,如果遇到偶数就把这个数之后的所有数往前移动一位,这样数组会留出一个空位,移动完毕之后把该偶数放到该空位即可.这样处理的话需要两次循环,一次是遍历,另一次是移位,所以时间复杂度是O(n2).下面是这种思路的实现代码(已被牛客AC): public void reOrd