设计一个算法,计算出n阶乘中尾部零的个数
样例
11! = 39916800,因此返回 2
挑战
O(logN)的时间复杂度
解答:
按照我这脑袋,先算阶乘,阶乘的结果一直用10去整除,能整除返回数值就加1。
然后第二个while循环出了问题,结果都运算不出来,天啊,还找不出怎么错的。
算法复杂度也远远超过log(n)。
困惑了一整天,终于发现是python3 中的除法出了问题,python3 中 / 变成了真除法,结果都用float型数据表示。程序中result = result/10 运行了一次while循环就停止了,天啊
换了python2 ,就能运行出结果了。
修改于2017/8/12
Python 3.6.0 (v3.6.0:41df79263a11, Dec 23 2016, 07:18:10) [MSC v.1900 32 bit (Intel)] on win32
Type "copyright", "credits" or "license()" for more information.
>>> 1/1
1.0
>>> 2/1
2.0
>>>
class Solution:
# @param n a integer
# @return as a integer
def trailingZeros(self, n):
result, i = 1, 1
while i <= n:
result = result * i
i += 1
answer = 0
while result % 10 == 0:
answer += 1
result = result/10
return answer
更巧妙的解答:
n! = 1×2×3×4×…×n
将阶乘结果分解质因数相乘形式。
n!=1×2×3×5×...=K×5x
结尾为0,只能是2*5的形式,2,4,6,8等等都能产生2,5的数量决定了最后0的数量。
K看成不相关的质因数相乘(2 有很多,也包括在了里面)。
然后有多少个质因数5,阶乘的结果最后就会有多少个0。
算法中,1~n相乘。
每一个5的倍数能先得到一个质因数5。(n/5个,python自动取整)
25的倍数能再多得到一个质因数5。((n/5)/5个)
125的倍数能再多得到一个质因数5。
依次类推,直到最后,得到所有的质因数5的个数。
class Solution:
# @param n a integer
# @return as a integer
def trailingZeros(self, n):
result = 0
while n != 0:
n /= 5
result += n
return result
算法复杂度: O(n)=2×log5(n)