給定十進位制表示的數字 N,找到其在任何基數(基數 b)下的位數。


問題陳述包括在任何基數 b 數制中表示 N 時找到其位數。最初,N 以基數 10 數制給出。

在問題中,我們將獲得輸入中的正整數 N,它將以基數 10 數製表示,以及大於 1 的正整數 b。我們的任務是找到 N 在基數 b 數制中表示時的位數。

任何以任何基數表示的數字,從右起每一位都表示該基數的冪的倍數,從 0 開始。

例如,當我們將 15 表示為基數 3 時。

它被表示為 120,即 $\mathrm{0*3^{0}+2*3^{1}+1*3^{2}=0+6+9=15}$

讓我們透過以下示例更好地理解問題。

輸入

N=16   b=5

輸出

2

解釋 - 在這裡,我們以基數 10 表示的形式給出 N,即 16。我們需要計算 N 在基數 5 中表示時的位數。

16 在基數 5 中的表示為 31,即 $\mathrm{1*5^{0}+3*5^{1}=1+15=16}$

16 在基數 5 中表示的位數為 2(即 31),這是我們所需的輸出。

輸入

N= 22    b=3

輸出

3

解釋 - 以基數 10 數製表示的 N 的值為 22,並且我們給定的基數等於 3。22 在基數 3 中的表示為 211,即 $\mathrm{1*3^{0}+1*3^{1}+2*3^{2}=1+3+18=22}$

因此,22 在基數 3 中表示的位數為 3,這是我們所需的輸出。

讓我們探索從樸素到高效解決方案的不同方法來計算任何數字 N 在基數 b 中表示的位數。

方法 1(樸素方法)

該解決方案的樸素方法將是將 N 表示為基數 b 數制並計算位數。

為了找到 N 在基數 b 中表示的位數,我們將建立一個函式。我們將初始化一個變數來儲存位數,並透過將 N 除以 b 來更新 N,直到 N 大於 0,並在每次迭代中增加位數。透過這種方式,我們可以計算 N 在基數 b 中表示的位數。

這可以更好地解釋為,要將任何數字表示為任何基數,我們取該數字對基數的模,它表示從右起每一位,並透過將該數字除以基數值來更新該數字,並重復此過程,直到該數字大於 0。

在 C++ 中實現該方法的步驟

  • 我們將建立一個函式來計算 N 在基數 b 中表示的位數。

  • 初始化一個變數來儲存位數。

  • 在 while 迴圈中迭代,直到 N 大於 0。

  • 在每次迭代中,透過將 N 除以 b 來更新 N,並將計數增加 1,因為要找到表示中的下一個左邊的位,我們取 N 對 b 的模,並使用更新後的 N。

  • 當 N 等於零時返回變數,這將是 N 在基數 b 數制中表示的位數。

示例

//C++ code to find the number of digits of N when represented in base b

#include <bits/stdc++.h>

using namespace std;

//function to calculate the number of digits of N in base b
int digits(long long int N, long long int b){
    //to store the number of digits of N in base b
    int a=0;
    
    //iterating to calculate the number of digits
    while(N>0){
        N = N/b; //update N by dividing it with b to find the next digit
        a++; //increase the count by 1 
    }
    
    return a;
}

int main()
{
    long long int N,b; //for taking input values
    
    N=58734;
    b=4;
    //calling the function
    cout<<"No. of digits of "<<N<<" in base-"<<b<<" :"<<digits(N,b)<<endl;

    return 0;
}

輸出

No. of digits of 58734 in base-4 :8

時間複雜度:O(log N),因為我們在 while 迴圈中迭代,直到 N 大於 0,並不斷將 N 除以基數值。

空間複雜度:O(1),因為沒有佔用額外的空間來查詢位數。

方法 2(高效方法)

我們可以使用數學中的對數函式的概念以更有效的方式解決問題。

N 在基數 b 中表示的位數與數字 N 和基數 b 之間存在數學關係。N 在基數 b 中表示的位數為(1 + N 以 b 為底的對數值)

讓我們透過下面的插圖更好地理解這種關係。

假設,N 在基數b中表示的位數為a

N 的值將落在範圍 $\mathrm{b^{a−1}<=N<b^{a}}$ 內,因為每一位都表示從 0 開始的基數的冪。因此,如果 N 有 a 位,則 N 的值必須等於或大於 $\mathrm{b^{a−1}}$(因為 a 從 0 開始)並且必須小於 $\mathrm{b^{a}}$(這是 b 的下一個冪)。

在等式兩邊取以 b 為底的對數,我們得到

$$\mathrm{(a−1)*\log_{b}b<=\log_{b}N}$$

任何數字以自身為底的對數始終為 1。因此,最終表示式將為

$\mathrm{a<=\frac{\log\:N}{\log\:b}+1}$,因為 $\mathrm{\log_{b}N}$ 可以寫成 $\mathrm{\frac{\log\:N}{\log\:b}}$

我們將使用上述公式在使用 C++ 中的 log() 函式的恆定執行時內計算 N 在基數 b 中的位數,該函式返回等於傳遞的引數的自然對數的值。

在 C++ 中實現該方法的步驟

  • 建立一個函式來計算 N 在基數 b 中的位數。

  • 初始化一個變數來儲存位數。

  • 使用匯出的公式,我們將計算位數。log() 函式可能會返回十進位制值,因此我們將使用 floor() 函式來獲取小於或等於 log() 函式返回值的最大整數,並確保 a 始終小於或等於 $\mathrm{\frac{\log\:N}{\log\:b}}$

  • 返回使用公式計算的位數,這將是我們的輸出。

示例

//C++ code to find the number of digits of N when represented in base b

#include <bits/stdc++.h>

using namespace std;

//function to calculate number of digits
int digits(long long int N, long long int b){
    //to store the number of digits of N in base b
    int a=0;
    
    a = floor( log(N) / log(b) ) + 1; //using the formula to calculate number of digits
    
    return a; //return number of digits
}

int main()
{
    long long int N,b; //for taking input values
    
    N=1e15; //storing 10^15 in N
    b=9;
    //calling the function
    cout<<"No. of digits of "<<N<<" in base-"<<b<<" :"<<digits(N,b)<<endl;

    return 0;
}

輸出

No. of digits of 1000000000000000 in base-9 :16

時間複雜度 - O(1),因為 log() 函式在恆定時間內返回該值

空間複雜度 - O(1),因為沒有佔用額外的空間。

結論

本文討論了在任何基數 b(將在輸入中給出)中表示 N 時查詢 N 的位數的概念。我們使用從樸素方法到使用 C++ 中對數函式概念的高效解決方案解決了該問題,並在恆定執行時和空間內實現了該問題。

希望您在閱讀本文後能夠理解問題以及解決問題的方法。

更新於: 2023 年 8 月 28 日

173 次瀏覽

開啟您的 職業生涯

透過完成課程獲得認證

開始
廣告