这个函数计算a ^ b的值并返回它。我的问题是m = log(b) 最好的情况是它进行m + 1次交互 但最坏的情况是什么?它进入while循环的次数是多少次?
This app protects user privacy. Please check www.example.com/Privacy.
答案 0 :(得分:3)
正如@EliSadoff在评论中所说,你的函数需要初始值result
。插入行
result = 1
在def
行之后。然后代码可以工作,这是隐式使用b
的二进制表示来快速获取取幂的标准方法。 (循环不变量是result * a ** b
的值保持不变,这表明了该算法的有效性。)
最糟糕的情况是每次通过if b % 2
循环执行while
行。只要b
小于2的幂,就会发生这种情况,因此b
二进制表示中的每个数字都是1。 while
循环条件while b>0
仍然只会m+1
次检查,但每个循环现在还有一些工作要做。
有几种方法可以加快代码速度。使用while b
而不是while b>0
和if b & 1
而不是if b % 2 = 1
。使用result *= a
而不是result = result*a
和a *= a
而不是a = a*a
和b >>= 1
而不是b = b // 2
。当然,这些都是相当小的改进。进一步加速循环的唯一方法是使用非结构化代码,我认为这在Python中是不可能的。 (还有一个a
的修改比必要的更好,但没有好的方法可以防止没有跳转到循环。)这个代码有一些变化,比如内部循环继续修改{{ 1}}和a
只要b
是偶数,但这并不总是更快。
最后的代码是
b
我清理了一些代码以更好地适应PEP8(Python风格标准)。请注意,代码中没有错误检查,尤其是确保def power(a, b):
"""Return a ** b, assuming b is a nonnegative integer"""
result = 1
while b:
if b & 1:
result *= a
a *= a
b >>= 1
return result
是非负整数。我相信如果b
是一个负整数,我的代码会得到一个无限循环,而你的代码会返回一个错误的结果。所以请做错误检查!另请注意,您的代码显示b
,这对于此类功能来说非常标准,但仍会让一些人感到意外。