昨日のコードでべき乗の計算を、10をn回掛けて行っていたが、Pythonはこれでよかったんだった。
a = 10**n
これだけでは面白くないので、再帰のコードを考えてみた。
def pow(a, n):
if n > 1:
half = n >> 1
return pow(a, half) * pow(a, n - half)
elif n == 1:
return a
elif n == 0:
return 1
else:
return 0print pow(10, 100)
例えば、29を計算するときに、半分にわけて考える。
29 = 24 * 25
こうやって分けていくと、いつか1乗になる。
ベンチマークしてみると、
import timedef pow(a, n):
if n > 1:
half = n >> 1
return pow(a, half) * pow(a, n - half)
elif n == 1:
return a
elif n == 0:
return 1
else:
return 0n = 100000
t1 = time.clock()
a = 10**n
t2 = time.clock()
b = pow(10, n)
t3 = time.clock()
c = 1
for i in range(n):
c *= 10
t4 = time.clock()print "%.4fs %.4fs %.4fs" % (t2 - t1, t3 - t2, t4 - t3)
0.0973s 0.4354s 4.8172s
再帰を使うと、単純に掛けていくだけよりは圧倒的に速いが、**より圧倒的に遅い。
**はバイナリ法を使っているのだろうか。