1021 个位数统计

1021 个位数统计 (15 分)

给定一个 k 位整数 N=d​k−1​​10​k−1​​+⋯+d​1​​10​1​​+d​0​​ (0≤d​i​​≤9, i=0,⋯,k−1, d​k−1​​>0),请编写程序统计每种不同的个位数字出现的次数。例如:给定 N=100311,则有 2 个 0,3 个 1,和 1 个 3。

输入格式:

每个输入包含 1 个测试用例,即一个不超过 1000 位的正整数 N。

输出格式:

对 N 中每一种不同的个位数字,以 D:M 的格式在一行中输出该位数字 D 及其在 N 中出现的次数 M。要求按 D 的升序输出。

输入样例:

100311

输出样例:

0:2
1:3
3:1

#include<cstdio>
#include<cstdlib>
#include<algorithm>
#include<iostream>
#include<string>
#include<vector>
using namespace std;

int main()
{
    string s;
    cin >> s;
    vector<int> num(10, 0);
    for (int i = 0; i < s.size(); i++) {
        num[s[i] - '0']++;
    }
    for (int i = 0; i < 10; i++) {
        if (num[i] > 0) cout << i << ":" << num[i] << endl;
    }
    return 0;
}
 

 

<think>我们有一个非负整数,需要统计其中每个数字0-9出现的次数,然后按格式输出。思路:1.将整数转换为字符串,然后遍历字符串的每个字符(每个字符就是数字),统计每个字符出现的次数。2.或者通过数学方法,不断取整数的最后一位(模10),然后除以10去掉最后一位,直到整数变为0。注意处理0的情况(如果整数为0,则0出现1次)。步骤:对于字符串方法:-将整数转为字符串。-初始化一个长度为10的数组(下标0-9),用于计数。-遍历字符串的每个字符,将字符转为数字(例如字符'0'转为0),然后对应下标计数加1。-最后遍历计数数组,按照格式输出。对于数学方法:-注意非负整数,包括0。-如果输入是0,则0出现1次。-否则,循环取余(%10)得到当前位的数字,计数,然后整数除以10,直到整数为0。-同样初始化一个长度为10的数组。输出要求:按照'数字:次数'逐行输出,注意数字从0到9。注意:如果某个数字没有出现,则其次数为0,也要输出。例如:输入1231,则输出:0:01:22:13:14:05:06:07:08:09:0我们分别用三种语言实现:1.C++实现(使用字符串方法):2.Java实现(使用字符串方法)3.Python实现(使用字符串方法,也可以使用数学方法,但字符串方法更简单)另外,也可以使用数学方法,这里为了简单,统一使用字符串方法。但是注意:如果整数非常大,字符串方法也是可以的,因为整数转字符串不会有精度损失(在语言支持的范围内)。代码示例: C++:#include<iostream>#include<string>#include<cctype>usingnamespace std;int main() {unsignedlong longn;//非负整数,使用unsignedlong long可以处理很大的整数cin >>n;//将整数转换为字符串string numStr =to_string(n);intcount[10]= {0};//初始化计数数组为0for(charc :numStr) {//字符减去'0'得到数字intdigit =c -'0';count[digit]++;}//输出0-9的统计for (int i=0;i <10; i++) {cout<< i<< ":" <<count[i] <<endl;}return0;}但是,如果输入是0,那么字符串就是"0",这样会统计0出现1次,正确。然而,上面的代码在输入0时没有问题。但是注意,如果输入的是0,那么字符串就是"0",所以会正确计数。 Java:import java.util.Scanner;public classDigitCount{public staticvoid main(String[]args){Scanner sc= newScanner(System.in);longn =sc.nextLong();//使用long,如果更大可以用BigInteger,但题目非负整数,一般long足够StringnumStr= Long.toString(n);int[]count =new int[10];for (int i=0;i <numStr.length();i++){char c= numStr.charAt(i);intdigit =c -'0';count[digit]++;}for(inti =0; i<10;i++){System.out.println(i+ ":" +count[i]);}}}注意:Java中如果输入的数非常大,可以使用BigInteger,然后转为字符串。但题目要求非负整数,一般情况long足够(最大到9,223,372,036,854,775,807),如果更大,则用BigInteger。Python:n =int(input().strip())#读取整数,但是接下来我们转为字符串,所以即使输入0也没问题#但是注意,如果输入0,那么字符串是'0's =str(n)count =[0]*10forchar ins:digit= int(char)count[digit] +=1for iin range(10):print(f"{i}:{count[i]}")但是,上述方法在输入0时都正确。然而,还有一种情况:如果输入的数字非常大,比如有1000位,那么用整数类型可能无法存储(在C++和Java中,除非用大数类),但题目要求非负整数,可能包括非常大的数(超出longlong范围)。所以,更通用的方法是直接读取字符串,然后统计字符串中每个字符(数字)出现的次数,跳过整数转换。因为题目要求非负整数,所以输入的字符串只包含数字字符(可能首位不是0,但如果是0,则只有一个0)。因此,我们可以直接读取字符串,然后统计。改进(适用于非常大的数字,无法用内置整数类型存储):-直接读取字符串(因为输入就是一个数字字符串)-然后统计字符串中每个字符(0-9)出现的次数。这样就不需要先转换为整数,避免了无法存储的问题。所以,更通用的方法:C++:#include <iostream>#include <string>#include <cctype>using namespacestd;intmain(){string numStr;cin>> numStr;//直接读取字符串intcount[10]= {0};//初始化计数数组为0for(charc :numStr) {//检查是否是数字字符if (isdigit(c)){int digit= c- '0';count[digit]++;}}//输出0-9的统计for (int i=0;i <10; i++) {cout<< i<< ":" <<count[i] <<endl;}return0;}但是,题目要求输入是非负整数,所以字符串中只会有数字字符,所以可以不用isdigit检查。Java:import java.util.Scanner;public classDigitCount{public staticvoid main(String[]args){Scanner sc= newScanner(System.in);StringnumStr= sc.next();//直接读取字符串int[] count= newint[10];for(inti =0; i< numStr.length(); i++) {charc =numStr.charAt(i);int digit= c- '0';count[digit]++;}for (int i=0;i <10; i++) {System.out.println(i +":"+ count[i]);}}}Python:s= input().strip()count =[0]*10for charin s:#将字符转换为整数digit= int(char)count[digit] +=1for iin range(10):print(f"{i}:{count[i]}")这样,即使数字非常大,也可以处理。但是,注意:输入可能包含前导零吗?题目说非负整数,通常输入不会包含前导零(除非是0本身),但我们的方法即使有前导零也没关系,因为统计的是每个数字出现的次数,包括前导零。例如:输入"00123",那么0出现了2次,1出现1次,2出现1次,3出现1次。但通常非负整数的字符串表示不会包含前导零(除非是0,但0只有一个0)。所以,我们按照字符串读取,统计所有字符。但是,题目要求统计的是非负整数中各个数字出现的次数。整数0的字符串表示就是"0",所以没有问题。因此,我们采用直接读取字符串的方法。下面分别给出三种语言的代码: C++代码:#include<iostream>#include<string>using namespacestd;intmain(){string s;cin >>s;intcount[10]= {0};//初始化为0for(charc :s){int digit= c- '0';if(digit>=0 &&digit <=9) {count[digit]++;}}for (int i=0;i <10; i++) {cout<< i<< ":" <<count[i] <<endl;}return0;} Java代码:importjava.util.Scanner;publicclass Main{public staticvoid main(String[]args){Scanner sc= newScanner(System.in);Strings =sc.next();int[]count =new int[10];for (int i=0;i <s.length(); i++) {charc =s.charAt(i);intdigit =c -'0';count[digit]++;}for(inti =0; i<10;i++){System.out.println(i+ ":" +count[i]);}}} Python代码:s= input().strip()count =[0] *10for charin s:digit =int(char)count[digit]+=1fori inrange(10):print(f"{i}:{count[i]}")注意:输入确保是非负整数的字符串,所以不会包含非数字字符。但是,如果输入是空字符串?题目非负整数,所以至少有一个字符(如果是0,则输入"0")。所以可以不用考虑空字符串。因此,以上代码可以满足要求。但是,如果用户输入的是0,那么输出中0出现1次,其他数字出现0次,符合要求。现在,按照要求输出代码,并解释。由于用户要求用Java/Python/C++,所以给出三种语言的代码。另外,注意输出格式:逐行输出'数字:次数'。我们开始写代码。</think>### 统计非负整数中数字出现次数的方法 要统计非负整数中每个数字(0-9)出现的次数并按格式输出,核心思路是将整数转换为字符串后遍历每个字符进行计数。以下是三种语言的实现方案: #### C++ 实现 ```cpp #include <iostream> #include <string> using namespace std; int main() { string numStr; cin >> numStr; // 直接读取字符串格式的数字 int count[10] = {0}; // 初始化计数器数组[0-9] for (char c : numStr) { int digit = c - '0'; // 字符转数字 if (digit >= 0 && digit <= 9) { count[digit]++; } } // 按格式输出结果 for (int i = 0; i < 10; i++) { cout << i << ":" << count[i] << endl; } return 0; } ``` #### Java 实现 ```java import java.util.Scanner; public class DigitCounter { public static void main(String[] args) { Scanner sc = new Scanner(System.in); String numStr = sc.next(); // 读取输入字符串 int[] count = new int[10]; // 初始化计数器数组 for (char c : numStr.toCharArray()) { int digit = c - '0'; // 字符转数字 if (digit >= 0 && digit <= 9) { count[digit]++; } } // 按格式输出结果 for (int i = 0; i < 10; i++) { System.out.println(i + ":" + count[i]); } } } ``` #### Python 实现 ```python num_str = input().strip() count = [0] * 10 # 初始化计数器列表 for char in num_str: digit = int(char) # 字符转数字 if 0 <= digit <= 9: count[digit] += 1 # 按格式输出结果 for i in range(10): print(f"{i}:{count[i]}") ``` ### 关键说明 1. **输入处理**:直接读取字符串格式的数字,避免大数溢出问题(如$10^{1000}$等超大整数)[^1] 2. **计数原理**: - 创建长度为10的数组/列表,索引对应数字0-9 - 遍历字符串中每个字符,转换为数字后增加对应计数器 - 字符转换:ASCII值减去`'0'`的ASCII值(C++/Java)或直接`int()`转换(Python) 3. **边界处理**: - 数字0:输入"0"时输出`0:1`(其他数字为0) - 前导零:会被正常计数(如"0012"中0出现2次) 4. **时间复杂度**:$O(n)$,其中$n$是数字的位数 ### 示例执行 **输入**: `2024` **输出**: ``` 0:1 1:0 2:2 3:0 4:1 5:0 6:0 7:0 8:0 9:0 ``` ### 相关问题 1. 如何处理包含负号或小数点的数字输入? 2. 如何扩展统计十六进制数字(0-9,A-F)的出现次数? 3. 当数字非常大(如$10^{100000}$)时,哪种实现方式性能最优? 4. 如何修改代码以输出出现次数大于0的数字? 5. 在分布式系统中如何统计超大数字的数字频率? [^1]: 输入处理直接读取字符串格式,避免数值类型溢出问题 [^2]: 字符与数字转换通过ASCII值计算实现 [^3]: 边界条件处理确保数字0的正确计数 [^4]: 前导零作为数字的一部分参与统计 [^5]: 时间复杂度与数字位数线性相关
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值