题目链接

题目描述

数字以 0123456789101112131415… 的格式序列化到一个字符串中,求这个字符串的第 index 位。
第5位是5,第13位是1,第19位是4等等

解题思路

假设index = 1001
序列的前10位是0~9这10个只有一位的数字,显然1001在这10个数字之后,因此这10个数字可以直接跳过,我们再从后面紧跟着的序列中找第991位的数字(1001-10 = 991)。
接下来的180个数字是90个10~99的两位数。由于991 > 180,所以991在所有的两位数之后。我们在跳过这90个两位数,找881位(991-90 = 881)。
接下来的2700位是900个100~999的三位数。由于881< 2700,所以第881位是某个三位数中的一位,由于881 = 270*3 + 1,这意味着881位是从100开始的第270个数字即370中的第一位,也就是7。

public int getDigitAtIndex(int index) {
   
    if (index < 0)
        return -1;
    int place = 1;  // 1 表示个位,2 表示 十位...
    while (true) {
   
        int amount = getAmountOfPlace(place);
        int totalAmount = amount * place;
        if (index < totalAmount)
            return getDigitAtIndex(index, place);
        index -= totalAmount;
        place++;
    }
}

/** * place 位数的数字组成的字符串长度 * 10, 90, 900, ... */
private int getAmountOfPlace(int place) {
   
    if (place == 1)
        return 10;
    return (int) Math.pow(10, place - 1) * 9;
}

/** * place 位数的起始数字 * 0, 10, 100, ... */
private int getBeginNumberOfPlace(int place) {
   
    if (place == 1)
        return 0;
    return (int) Math.pow(10, place - 1);
}

/** * 在 place 位数组成的字符串中,第 index 个数 */
private int getDigitAtIndex(int index, int place) {
   
    int beginNumber = getBeginNumberOfPlace(place);
    int shiftNumber = index / place;
    String number = (beginNumber + shiftNumber) + "";
    int count = index % place;
    return number.charAt(count) - '0';
}