每日一题:Leetcode-440 字典序的第K个小数字

力扣题目

解题思路

java代码

力扣题目:

给定整数 n 和 k,返回  [1, n] 中字典序第 k 小的数字。

示例 1:

输入: n = 13, k = 2
输出: 10
解释: 字典序的排列是 [1, 10, 11, 12, 13, 2, 3, 4, 5, 6, 7, 8, 9],所以第二小的数字是 10。

示例 2:

输入: n = 1, k = 1
输出: 1

解题思路:

算法原理
这道题通过逐步试探的方法在按字典序排列的数字序列中找到第 k 个数字。

思路

  1. 从数字 1 开始,计算以当前数字 curr 为前缀能构成的数字个数 steps 。
  2. 如果 steps 小于 k ,说明第 k 个数字不在以 curr 为前缀的数字中,将 curr 增加 1 ,并减少 k 的值。
  3. 如果 steps 大于等于 k ,说明第 k 个数字在以 curr 为前缀的数字中,将 curr 乘以 10 ,继续在这个前缀下寻找,同时减少 k 的值。

代码分析

  • findKthNumber 方法中,通过一个循环不断调整 curr 的值来逼近第 k 个数字。
  • getSteps 方法用于计算以给定数字 curr 为前缀能构成的数字个数。

时间复杂度
平均情况下,时间复杂度为  ,因为每次调整 curr 时,计算前缀的数字个数也需要一定的时间。

空间复杂度
空间复杂度为  ,只使用了固定的几个变量,空间开销恒定。

java代码:

package org.example;

public class Leetcode440 {
    public static void main(String[] args) {
        System.out.println(new Leetcode440().findKthNumber(13, 2));
    }
    public int findKthNumber(int n, int k) {
        int curr = 1;
        k--;
        while (k > 0) {
            int steps = getSteps(curr, n);
            if (steps <= k) {
                k -= steps;
                curr++;
            } else {
                curr = curr * 10;
                k--;
            }
        }
        return curr;
    }

    public int getSteps(int curr, long n) {
        int steps = 0;
        long first = curr;
        long last = curr;
        while (first <= n) {
            steps += Math.min(last, n) - first + 1;
            first = first * 10;
            last = last * 10 + 9;
        }
        return steps;
    }

}

更多详细内容同步到公众号,感谢大家的支持!

每天都会给刷算法的小伙伴推送明日一题,并且没有任何收费项

  • 7
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

L.2626

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值