题目

小R每天对小J滔滔不绝,小J想证明小R说的内容都是重复的废话。给定一段只含英文字符和数字的字符串(可能含空格),统计数字 0-9 和字母 A-Z(大小写不区分)各出现多少次,并画出柱状统计图。

输入:共1行,一个字符串,字符数量不超过1000个。
输出:一个柱状图,每格用空格隔开,* 表示该字符有计数,- 表示没有,最后一行为标签 0 1 2 ... 9 A B ... Z

样例:

输入

I1think2programming3is4something5that6allows7me8to9achieve0a!great@sense#of$accomplishment.

输出

- - - - - - - - - - - - - - * - - - - - - - - - - - - - - - - - - - - -
- - - - - - - - - - * - - - * - - - * - - - - - - - - - - * - - - - - -
- - - - - - - - - - * - - - * - - - * - - - * - * - - - * * - - - - - -
- - - - - - - - - - * - - - * - - * * - - - * * * - - - * * - - - - - -
- - - - - - - - - - * - - - * - * * * - - - * * * - - - * * - - - - - -
- - - - - - - - - - * - * - * - * * * - - * * * * - - * * * - - - - - -
- - - - - - - - - - * - * - * - * * * - - * * * * * - * * * - - - - - -
* * * * * * * * * * * - * - * * * * * - * * * * * * - * * * - * * - - -
0 1 2 3 4 5 6 7 8 9 A B C D E F G H I J K L M N O P Q R S T U V W X Y Z

思路

getline 读整行字符串(因为可能含空格)。遍历每个字符,用 isdigitisalpha 判断类型——注意判断的是字符 s[c],而不是循环索引 c——将结果累计到 cnt[36]:数字映射到下标 s[c]-'0',字母先 toupper 再映射到 toupper(s[c])-'A'+10

统计完后找最大值 maxVal,再倒序从第 maxVal 行到第 1 行输出:内层循环遍历 36 列,cnt[列] >= 当前行 输出 *,否则输出 -,每格后跟一个空格。最后一行直接输出固定标签。

C++ · p34.cpp
#include<bits/stdc++.h>
using namespace std;

int main(){
    string s;
    getline(cin,s);

    int cnt[36]={0};

    for(int c=0;c<s.size();c++){
        if(isdigit(s[c])){
            cnt[s[c]-'0']++;
        }else if(isalpha(s[c])){
            cnt[toupper(s[c])-'A'+10]++;
        }
    }

    int maxVal=0;
    for(int c=0;c<36;c++){
        if(cnt[c]>maxVal)maxVal=cnt[c];
    }

    for(int c1=maxVal;c1>0;c1--){
        for(int c2=0;c2<36;c2++){
            if(cnt[c2]>=c1)cout<<"* ";
            else cout<<"- ";
        }
        cout<<endl;
    }
    cout<<"0 1 2 3 4 5 6 7 8 9 A B C D E F G H I J K L M N O P Q R S T U V W X Y Z"<<endl;

    return 0;
}

复杂度分析

  • 时间复杂度:O(n + maxVal × 36),n 为字符串长度,输出部分最多 1000 × 36 次。
  • 空间复杂度:O(1),cnt 数组固定大小 36。
今日感受

看起来复杂的题,拆开来一步步做也不难。有一个容易踩的坑:用 isdigitisalpha 判断时,传入的应该是字符 s[c],而不是循环索引 c——索引只是个数字,字符才是真正要判断的内容。输出部分记得倒序遍历行,从最高处往下画才能得到正确的柱状图。

← 返回菜鸟的coding