藍橋杯 演算法提高 JOE的算數 快速冪取模

2021-10-02 22:26:48 字數 1566 閱讀 8667

資源限制

時間限制:1.0s 記憶體限制:256.0mb

問題描述

有一天,joe終於不能忍受計算a^ b%c這種平凡的運算了。所以他決定要求你寫乙個程式,計算a^b%c。

三個非負整數a,b,c;

輸出格式

乙個整數ans,表示a^b%c;

樣例輸入

7 2 5

樣例輸出

4資料規模和約定

30% a <= 100, b <= 10^4, 1 <= c <= 100

60% a <=10^4, b <= 10^5, 1 <= c <= 10^4

100% a <=10^6, b <= 10^9, 1 <= c <= 10^6

解題思路

本題是快速冪取模的裸題。

冪指數b可能達到10^9,所以用for迴圈逐個做乘法肯定會超時,而且運算結果是個天文數字。根據題目給的提示,可以每一次都把b降低一倍,這也就是快速冪演算法,可以把時間複雜度降低為o(log n)。

根據數**演算法則,b為偶數時:a^ b=(a^ (b/2))^ 2 =(a^2) ^b/2

b為奇數時: a^ b=((a^ (b/2))^ 2)*a=((a^2) ^b/2) *a

比如記a為a,則

a ^ 11= a ^11=((a^2) ^5) *a 此時 a^2 為新的底數,記為b,11/2=5為新的指數。

((a^2) ^5)=b ^5=((b ^2) ^2) * b 同理 b ^2 即a ^4 是新的底數,記為c,新的指數是5/2=2

((b ^2) ^2)=(( c) ^ 2)=((c ^2) ^1) 繼續 c ^2 即 a ^8 是新的底數,記為d,新的指數為2/2=1。

((c ^2) ^1)=((d) ^1)=((d ^ 2) ^ 0) * d 此時指數為1/2=0,結束迭代。

即 a ^ 11=a * b * c=a ^1 * a ^ 2 * a ^ 8

從上面可以得到啟發:

1.a b c d都各自是前面的平方,所以每一輪迭代用tmp=tmp* tmp 來模擬這個過程。

2*.只有當指數為奇數的時候,末尾才要補乘以底數。(上面已加粗顯示)

用二進位制很好理解,把b轉換為二進位制數,二進位制每一位的權值都是前一位的兩倍,對應著tmp*tmp,例如11(10)=1011(2)=2 ^ 3 +2 ^ 1 + 2 ^ 0 =8 + 2 + 1 。

還要注意取模,根據模運算的性質,得 a ^ b mod c = ((a mod c) ^ b) mod c

#include

using

namespace std;

intmain()

printf

("%lld"

,result)

;return0;

}

演算法提高 JOE的算數

問題描述 有一天,joe終於不能忍受計算 ab mod c 這種平凡的運算了,所以他決定要求你寫乙個程式,計算 ab mod c。輸入格式 三個非負整數 a,b,c 輸出格式 乙個整數 ans,表示 ab mod c 樣例輸入 7 2 5 樣例輸出 4資料範圍 對於 30 的測試資料 a 100,b...

藍橋杯 演算法提高 快速冪

資源限制 時間限制 1.0s 記憶體限制 256.0mb 問題描述 給定a,b,p,求 a b mod p。輸入格式 輸入共一行。第一行有三個數,n,m,p。輸出格式 輸出共一行,表示所求。樣例輸入 2 5 3 樣例輸出 2資料規模和約定 共10組資料 對100 的資料,a,b為long long範...

藍橋杯 演算法提高 change

資源限制 時間限制 1.0s 記憶體限制 256.0mb 問題描述 陣列a中共有n個元素,初始全為0。你可以對陣列進行兩種操作 1 將陣列中的乙個元素加1 2 將陣列中所有元素乘2。求將陣列a從初始狀態變為目標狀態b所需要的最少運算元。輸入格式 第一行乙個正整數n表示陣列中元素的個數 第二行n個正整...