算法學習之數字序列中某一位的數字

題目:數字以0123456789101112131415···的格式序列化到一個字符序列中。在這個序列中,第5位(從0開始計數)是5,第13位是1,第19位是4,等等。請寫一個函數,求任意第n位對應的數字。

書上的思路:

如輸入1001

0~9十個數(從第0位開始)顯然小於1001,所以從雙位數中查找。

10~99,個數爲10*9*2=180,顯然也小於1001-10=991。

100~999,個數爲100*9*3 = 2700,2700大於991-180=811。

所以所求數字處在三位數當中。三位數已100開頭,而811 = 3*270+1,因爲100本身也佔三位所以100+270也正是所求位數對應的數字,即370,餘數也就是所求位數所處的索引。即7即爲所求數字。

   public static int digitAtIndex(int index) {
        if(index==0) {
            return 0;
        }
        int digit = 1; // 記錄數字當前是幾位數
        while(true) {
            int curCount = getCurCount(digit); // 獲取當前數字個數
            if(index<curCount) { // 說明在本區間內,進行查找
                return getDigit(digit,index);
            }else {
                index-=curCount;
                digit++;
            }
        }
    }

    private static int getDigit(int digit, int index) {
        int curBeginNumber = getCurBeginNumber(digit); // 獲取當前區間開始的首個數,如兩位數的首個爲10
        int curNumber = curBeginNumber+index/digit; // 所求數字處在哪個數字裏如第19位處在14這個數字中
        int rigthNumber = digit - index%digit; // 從左側餘數轉爲右側 ,這裏也可以用其他方法找到所需數字
        for (int  i = 1 ;i< rigthNumber;i++) { // 轉爲右側記數後,去除右側rigthNumber-1位數
            curNumber/=10;
        }
        return curNumber%10; // 到這一步其實像370這個數字已近變爲37,只需對個位取餘就找到目標數字了
    }

    /**
     *
     *  獲取當前數字個數
     * @param digit
     * @return
     */
    private static int getCurBeginNumber(int digit) {
        if(digit==1) {
            return 0;
        }

        return (int) Math.pow(10,digit-1);
    }

    /**
     * 獲取當前數字個數,如0~9爲十個,從0位開始到第0位
     * @param digit
     * @return
     */
    private static int getCurCount(int digit) {
        if(digit==1) {
            return 10;
        }

        return (int) (9*  Math.pow(10, digit - 1)*digit);
    }

                      

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章