在10进制和2进制中,从0到N总共包含1的数目
来源:互联网 发布:不用网络的监控摄像头 编辑:程序博客网 时间:2024/05/17 05:02
这是一道比较传统的面试题,自己写了个10进制的求1个数的程序,后来在《编程之美》中发现上面的解法更好一些,随后有用它的方法重写了一遍2进制下的求解方法。
程序源码请点击这里下载。
对于自己写的10进制程序:主要思想还是从前期的分析得出来的:
1、先统计N的相应位置所对应的累加和数组
2、从前到后,根据所当前位置对应的位数,进行累加,即:
1)当当前为为1时,当前位置所对应的单位个数+低位数值+1;
2)当当前为为0时,用当前位置的数值*当前位置为所对应的1的单位总个数+低位数值;
3、求出当前位总和后,向下一位移位,递归累加
程序主要源码如下:
long long numCount[32] = {0};//function entranceunsigned long long getDecimal(unsigned long long num){ unsigned long long result = 0L; unsigned long long temp = num; unsigned long long bNum = 10; int nLength = 1; //get the length of number while(temp /= 10) { nLength++; } //init the first one numCount[0] = 1; //Record the sum of the big number for pretreatment; for(int i = 1; i < nLength - 1; i++) { numCount[i] = bNum + (numCount[i-1] * 10); bNum *= 10; } result = statisticTen(num, bNum, nLength); return result;}/** @param theNume : the number you wanna calculate * @param bNum : the index of directing current number* @param Length : the length of theNum*/int statisticTen(unsigned long long theNum, unsigned long long bNum, int Length){ //stop the recursion process if(Length < 2 || theNum == 0) { if(theNum != 0) return 1; else return 0; } int fn = 0; unsigned long long sn = 0L; fn = theNum / bNum;//get count of higher number sn = theNum % bNum;//get count of lower number unsigned long long temp = 0L; if(fn == 1) { //we can regards numCount[Length - 2] as higher number temp = sn + 1 + numCount[Length - 2]; } else { temp = fn * numCount[Length - 2] + bNum; } //go to the next recursion return temp += statisticTen(sn, bNum/10, --Length);}
2进制程序主要是根据《编程之美》中的统计思想的重写,其中并为使用递归,效率更高,统计方法大同小异,具体推导过程,详见《编程之美》2.4节
程序主要代码如下:
//function entranceint statisticBin(long long theNum){ unsigned long long iCount = 0L; unsigned int iFactor = 0; unsigned long long iLowerNum = 0L; unsigned int iCurrNum = 0; unsigned long long iHigherNum = 0L; while(theNum >> iFactor != 0) { iLowerNum = theNum - ((theNum >> iFactor) << iFactor); iCurrNum = (theNum >> iFactor) & 0x01; iHigherNum = theNum >> (iFactor + 1); switch(iCurrNum) { case 0: iCount += iHigherNum * (1 << iFactor); break; case 1: iCount += iHigherNum * (1 << iFactor) + iLowerNum + 1; break; } iFactor++; } return iCount;}
测试:
对于10进制,选取了f(n)=n的形式,来确定结果的正确性。
对于2进制,选取了111010100010101010101010这个二进制数,其结果也与期望相符。
如图所示:
小结:
可以看到,虽然统计思想大同小异,但是具体实现时却大为不同,自己的程序使用了数组和递归,在时间和空间复杂度上都大不如后者,通过此题说明以下几点:
1、在程序的分析初期,一定要总结归纳,寻找其中的规律,为编程做好理论基础
2、在工程实践中,一定要摆脱大脑特定思维,从计算机效率出发来思考和解决问题。
3、编程是一个探索其中,也乐在其中的过程,要勤学勤练,保持正确的思考问题、解决问题的方法。
0 0
- 在10进制和2进制中,从0到N总共包含1的数目
- 从1到n的数中总共包含1的个数
- 【100题】求从1到n的数中,总共包含了多少个1
- 求从1到n的数中,总共包含了多少个1
- m*n的方格,从左下角走到右上角,只能向右和向上,总共的路径
- 集合[1,2,3,...,n]总共包含n! 独特排列。 给出n和k 返回第k个排列。
- 对于一个数字,我们可以直观的了解到它所含有的数字,例如: 3243中包含1个2、2个3、1个4。 那么,给你一个数n,求从1到n之间的所有这些数字中,总共包含多少个m。
- 整数的二进制数中1的数目,1-N中1的总共个数,如何判断一个数是否为2的整数次幂.
- 求从1到N中1的出现的数目
- 1.2 从0到n,共包含多少个2?
- 【编程之美】2.4从1到N中1出现的数目
- 迷宫问题2-在给定的迷宫中计算从起点到终点的路径数目
- 整数中出现1的数目(从1到n的整数中出现1的次数)
- 【编程之美】2.4从1到N中1出现的数目----出现任意一个数的个数。
- 数一数1到n出现1的数目
- 计算0到N中包含数字1的个数
- 0到N中包含数字1的个数
- 从1到n个自然数中,各个数位包含1的个数
- 对象排序
- python的一个编解码错误
- Jquery选择器要注意空格问题
- 建造者模式
- Android如何防止apk程序被反编译
- 在10进制和2进制中,从0到N总共包含1的数目
- 黑马程序员-数组排序
- Android实现仿QQ登录可编辑下拉菜单
- 黑马程序员_高新技术
- leetcode - Pascal's Triangle
- xu han shu ji suan tu xing mian ji
- phoenix入门
- 第六章作业
- CPA,CPS,CPC,PPC,UV,PV等术语