日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

求数字序列中的第n位对应的数字

發(fā)布時(shí)間:2023/12/13 编程问答 22 豆豆
生活随笔 收集整理的這篇文章主要介紹了 求数字序列中的第n位对应的数字 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

文章目錄

  • 題目
  • 思路
  • 代碼
  • 復(fù)雜度分析
  • 致謝


題目

數(shù)字以0123456789101112131415…的格式序列化到一個(gè)字符序列中。在這個(gè)序列中,第5位(從下標(biāo)0開(kāi)始計(jì)數(shù))是5,第13位是1,第19位是4,等等。

請(qǐng)寫(xiě)一個(gè)函數(shù),求任意第n位對(duì)應(yīng)的數(shù)字。


思路

我們注意到,如果:

  • 將 01234567891? 中的每一位稱為 位 ,記為 n ;
  • 將 10,11,12,? 稱為 數(shù)字 ,記為 num ;
  • 數(shù)字 10 是一個(gè)兩位數(shù),稱此數(shù)字的 位數(shù) 為 2 ,記為 digit ;
  • 每 digit 位數(shù)的起始數(shù)字(即:1,10,100,?),記為 start 。
  • 個(gè)位數(shù)共有 1 ~ 9 九個(gè)數(shù)字,稱個(gè)位數(shù)的 數(shù)字?jǐn)?shù)量 為 9 ,記為 num_count 。
  • 十位數(shù)共有 10~99 90個(gè)數(shù)字,每個(gè)數(shù)字有兩位,共占序列化 90*2=180 位,稱十位數(shù)的 數(shù)位數(shù)量 為 180 , 記為 count 。
  • 可以得到下表(個(gè)位數(shù)不計(jì)入0):

    數(shù)字范圍位數(shù)數(shù)字?jǐn)?shù)量共占序列化多少位
    1~9199
    10~99290180
    100~99939002700
    ……………………
    start~enddigit9*start9 * start * digit

    可以得到三個(gè)公式:

  • 位數(shù)遞推公式 digit = digit + 1
  • 起始數(shù)字遞推公式 start= start * 10
  • 數(shù)字?jǐn)?shù)量計(jì)算公式 num_count = 9 * start
  • 數(shù)位數(shù)量計(jì)算公式 count = 9 * start * digit
  • 我們可以將求 第n位對(duì)應(yīng)的數(shù)字 求解過(guò)程分為以下幾步:

  • 確定 n 所在 數(shù)字 的 位數(shù)digit ;
  • 確定 n 所在的 數(shù)字num ;
  • 確定 n 是 num 中的哪一位。
  • 第一步:

    在幾位數(shù)的范圍內(nèi)?

    while(n>count){n -= count;start *= 10;digit++;count = 9*start*digit; }

    第二步:

    是哪個(gè)數(shù)字?

    int num = start+(n-1)/digit;

    為什么是 (n-1)/digit 而不是 n/digit ?

    首先看一張圖:

    以兩位數(shù)為例,當(dāng)執(zhí)行完 n=n-9 之后,n 與各個(gè)兩位數(shù)數(shù)位的對(duì)應(yīng)關(guān)系如上圖所示。以13為例,當(dāng)我們知道 n=7(13中的1) 時(shí),由 n/2=3 可得 n 是十位數(shù)起始數(shù)字之后的第三個(gè),但是當(dāng) n=8(13中的3) 時(shí),由 n/2=4 得到 n 對(duì)應(yīng)的是十位數(shù)起始數(shù)字之后的第四個(gè),這是錯(cuò)誤的,十位數(shù)起始數(shù)字之后的第四個(gè)是 14 而非 13 ,因此計(jì)算時(shí)需要將 n 進(jìn)行 減一操作,因?yàn)槲覀儗⑵鹗紨?shù)字看作 第0個(gè)數(shù) 而非 第1個(gè)數(shù) 。

    為什么是 (n-1)/digit 而不是 n/digit-1?

    仍然以兩位數(shù)為例,當(dāng) n 對(duì)應(yīng)非起始數(shù)字時(shí),兩種算法是沒(méi)有區(qū)別的,但是當(dāng) n 對(duì)應(yīng)起始數(shù)字時(shí),不論 n=0 or n=1 , (n-1)/digit 的計(jì)算結(jié)果都為 0 ,而 n/digit-1 的計(jì)算結(jié)果都為 -1 。 (n-1)/digit 對(duì)應(yīng)的數(shù)字 num = start + 0 = 10 ,正確;而 n/digit-1 對(duì)應(yīng)的數(shù)字 num = start + (-1) = 9 ,變成了個(gè)位數(shù),錯(cuò)誤。

    總而言之,對(duì) n 進(jìn)行 減一操作 是因?yàn)?起始數(shù)字應(yīng)視為 start + 0,雖然它是兩位數(shù)里面的 第一個(gè) 數(shù)字,但是我們?cè)诠嚼镎f(shuō)的 第幾個(gè) 是 該數(shù)字相對(duì)于起始數(shù)字 而言的,因此要統(tǒng)統(tǒng)減一。而之所以不是 先除再減 而是 先減再除 是因?yàn)?要考慮邏輯順序?qū)ζ鹗紨?shù)字的影響 。

    第三步:

    處于對(duì)應(yīng)數(shù)字的哪一位?

    num = s[(n-1)%digit] - '0';

    (n-1)%digit 計(jì)算的便是對(duì)應(yīng)的 數(shù)位 ,n減一的原因和第二步中相同,不再贅述。


    代碼

    class Solution { public:int findNthDigit(int n) {long long start=1, count=9, digit=1;while(n>count){n -= count;start *= 10;digit++;count = 9*start*digit;}int num = start+(n-1)/digit;//所在數(shù)字string s = to_string(num);num = s[(n-1)%digit] - '0';//處于所在num的哪一位return num;} };

    復(fù)雜度分析

    時(shí)間復(fù)雜度 O(logn) : 所求數(shù)位 n 對(duì)應(yīng)數(shù)字 num 的位數(shù) digit 最大為 O(log n) ;第一步最多循環(huán) O(log n) 次;第三步中將 num 轉(zhuǎn)化為字符串使用 O(log n) 時(shí)間;因此總體為 O(log n) 。

    空間復(fù)雜度 O(logn) : 將數(shù)字 num 轉(zhuǎn)化為字符串 str(num) ,占用 O(logn) 的額外空間。


    致謝

    思路中的部分想法、復(fù)雜度分析源于K神的題解,鞠躬致謝。

    創(chuàng)作挑戰(zhàn)賽新人創(chuàng)作獎(jiǎng)勵(lì)來(lái)咯,堅(jiān)持創(chuàng)作打卡瓜分現(xiàn)金大獎(jiǎng)

    總結(jié)

    以上是生活随笔為你收集整理的求数字序列中的第n位对应的数字的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

    如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。