一、题目
给定一个十进制的正整数,写下从1开始,到N的所有整数,然后数一下其中出现“1”的个数。
要求: 写一个函数 f(N) ,返回1 到 N 之间出现的 “1”的个数。
例如 f(12) = 5。 在32位整数范围内,满足条件的“f(N) =N”的最大的N是多少。
二、设计思想
对于这道题目,输入一个正整数,返回从1开始到这个数之间出现过的所有“1”的个数,我的思路是这样的,
1、先要将这个数是几位数得出来;
2、用一个for 循环将数字中德每一位存到数组中,以备后面使用;
3、因为要得到总的1的个数,分别计算个位、最高位、和其它位的1的个数;
4、最后将所有的求和。
三、设计代码
1 import java.util.*; 2 3 class ZhaoYi 4 { 5 public static void main(String[] args) 6 { 7 System.out.print("请输入一个正整数:"); 8 Scanner sc = new Scanner(System.in); 9 int num = sc.nextInt(); 10 11 int m = zhaoYi(num); // 12 System.out.println("从1到该数字之间出现“1”的次数是:"+m+"次"); 13 14 } 15 public static int weiShu(int b) //可以得到输入的数字的位数 16 { 17 int temp = 0; 18 for (int i=1;i<32 ;i++ ) 19 { 20 if (b/((int)Math.pow(10,i))==0) 21 { 22 temp = i; 23 break; 24 } 25 } 26 return temp; 27 } 28 29 public static int zhaoYi(int a) //出现1的个数 30 { 31 int[] arr = new int[32];//一个32位的数组 32 int[] sum = new int[32];//一个32位的数组,用来求和 33 //int weiShu = 0; 34 int SUM = 0; //初始化最后的求和数 35 int n = a; //转移 36 int ws = weiShu(a); //得到输入数的位数 37 38 for (int i=0;i<ws ;i++ ) //将输入的数每一位都存到一个数组中 39 { 40 arr[i] = n%10; 41 n = n/10; 42 } 43 44 for (int i=0;i<ws ;i++ ) //根据找出的规律,计算每一位上出现1个数的和 45 { 46 if (i==0) 47 { 48 //个位出现一的个数 49 if (arr[i]==0) 50 sum[i] = a/10; 51 else 52 sum[i] = a/10+1; 53 54 } 55 else if(i==ws-1) 56 { 57 //最高位 58 if (arr[i]==1) 59 sum[i] = a%((int)Math.pow(10,i)) + 1; 60 else 61 sum[i] = (int)Math.pow(10,i); 62 } 63 else //其他位 64 { 65 if(arr[i] == 0) 66 sum[i] = (a/((int)Math.pow(10,i+1)))*((int)Math.pow(10,i)); 67 else if(arr[i] == 1) 68 sum[i] = (a/((int)Math.pow(10,i+1)))*((int)Math.pow(10,i)) + a%((int)Math.pow(10,i)) + 1; 69 else 70 sum[i] = (a/((int)Math.pow(10,i+1)))*((int)Math.pow(10,i)) + (int)Math.pow(10,i); 71 } 72 73 SUM += sum[i]; 74 } 75 return SUM; //返回最终的次数 76 } 77 }
四、结果截图
五、心得体会
这次实验的思路比较明确,就是要将输入的数字的 每一位出现的1的个数得到,通过分析规律,将每一位出现1的个数,加起来,最后的到总和。每一位上的情况都能划分成是0,是1,和其余的数的区别,不过在编写的时候,也遇到了一点错误,就是在得到数的位数的时候,一直没能成功,其实这是一个非常简单的问题,最后也解决了。