マスターの説明を見た後、理論は次のとおりです: Fast Power Algorithm (ゼロから段階的に最適化するための、ネットワーク全体に関する最も詳細なガイド) - CSDN ブログ
例: 整数の底による整数の累乗を求め、整数 num_mod を累乗します。
Python コードは次のとおりです。
import time
def normalPower(base, power, num_mod):
res = 1
for i in range(int(power)):
res = res * base % num_mod
return res
def fastPower(base, power, num_mod):
res = 1
while power > 0:
if power & 1: # 优化掉: power % 2 == 1
res = res * base % num_mod
power >>= 1 # 优化掉: power = power // 2
# base = (base * base) % num_mod
temp_base = base % num_mod
base = temp_base * temp_base % num_mod
return res
if __name__ == '__main__':
time1 = time.time()
print(fastPower(2, int(1e8), 1000))
print("fastPower Time:", round((time.time() - time1) * 1000, 5), 'ms')
time2 = time.time()
print(normalPower(2, int(1e8), 1000))
print("normalPower Time:", round((time.time() - time2) * 1000, 5), 'ms')
出力は次のとおりです。
数値をもう少し大きくしてみましょう:
print(fastPower(int(1e200), int(1e100), 1000))
所要時間はまだ 0.0ms です。
それを分析しましょう:
1. 1 つ目は行列の高速累乗であり、従来の方法と比較して、高速化効果は直接ミリ秒レベルです。
2.「ビット演算」は2のべき乗>>= 1の演算を最適化します
# 最適化: power = power // 2
3. 「AND 演算」はべき乗 & 1 の偶数判定を最適化します: # 最適化: power % 2 == 1
4. ここでは、base の値が非常に大きい可能性があることを考慮した、私の個人的な最適化を示します。
# 次の 2 行は out を最適化します。base = (base * Base) % num_mod
temp_base = Base % num_mod
Base = temp_base * temp_base % num_mod
全体最適化後は、時間が0.0msを超えるケースは基本的には存在しません。