今天看到一道面试题,百度的,忘记哪一年了。具体题目如下:
对任意输入的正整数N,编写C程序求N!的尾部连续0的个数,并指出计算复杂度。如:18!=6402373705728000,尾部连续0的个数是3。
(不用考虑数值超出计算机整数界限的问题) 。
***************
在做校车来的路上随便想想,感觉没有思路,没有感觉,后来突然想到这是具体运算的东西,前段时间好像听过组成原理,讲过运算器的东东。从构思到调试成功,快两个小时了,但是对我来说是头一次啊~~~
思路很简单:尾数中含有0的个数,加上尾数为2和尾数为5的个数取最小值,因为末尾0的个数主要是有0,2,5这三个数组成的。但是调试的时候好难,很快把代码写出来,调试用了四分之三还多的时间。不过好在结果出来了。
把自己做的很挫的源码还是贴出来供人好好的批评一番吧。
//
#include "stdio.h"
int backZeros(int n){
int count = 0;//从后往前累加0的个数
/*m存放被除数(初始余数)和之后每次产生的新的商*/
int m=0;
int divider =10;//除数
int mod=0;//余数
/*可以不用twoCount了,因为twoCount总是大于fiveCount*/
int twoCount=0;//阶乘中总共含有有效的2的个数
int fiveCount=0;//阶乘中总共含有有效的5的个数
int number=1;//索引从1到n
printf("enter .../n");
//计算从1*2*..*n里面0的个数,2 的个数,5的个数
for(number;number<=n;number++){
m = number;
printf("current number is %d/n",number);
mod = number%divider;
if(mod==2){
twoCount++;
//printf("current twoCount is %d/n",twoCount);
}
else if(mod==5){
fiveCount++;
//printf("current fiveCount is %d/n",fiveCount);
}
else{
while(mod==0){
count++;
m = m/divider;//左移一位,得到的商是新的被除数了。。。
mod = m%divider;
printf("current Count is %d/n",count);
}
if(m%divider==2)
twoCount++;
if(m%divider==5)
fiveCount++;
}
}//end for
printf("current fiveCount is %d/n",fiveCount);
count += fiveCount;
return count;
}
int main(){
int result=0;
printf("enter main()/n");
result=backZeros(180);
printf("result = %d/n",result);
return 0;
}