题目描述
给定一个字符串,统计其中连续出现的相同字符个数。
输入描述
一个非空字符串(长度不超过100,仅由小写字母组成)。
输出描述
按从左到右字符出现的顺序,输出每个字符连续出现的个数。
其中每个字符输出一行,每行以空格为分隔,输出该字符与出现的个数。
样例1
输入
abbbcc
输出
a 1
b 3
c 2
样例2
输入
ccbbc
输出
c 2
b 2
c 1
这道题刚开始没有仔细阅读,仅仅以为是统计相同字母出现的次数,然后按输入的字母顺序打印出来 字母 字母出现次数, 于是就写了如下代码:
#include <cstdio>
#include <cstring>
char arr[110];
int cnt[110];//统计字母出现的次数
int main() {
scanf("%s", &arr);
int len = strlen(arr);
for (int i = 0; i < len; i++) {
cnt[arr[i]-'a']++; //将字母a,b,c,d...对应为数组cnt的下标0,1,2,3...。
}
for (int m = 0; m < 26; m++) {//字母有26个,由上面注释易知z对应下标为25
if (cnt[m] != 0) { //cnt[m]不等于0,说明该下标对应字母出现过,并且存的数字就是该字母出现的次数
printf("%c %d\n", m + 'a', cnt[m]);//m + 'a'是将下标0,1,2,3...转换为要打印的字母a,b,c,d...
}
}
return 0;
}
但是题目要求是统计连续出现的相同字符个数,如abbaaccb,应该输出:
a 1
b 2
a 2
c 2
b 1
于是我做了如下修改:
大致思路:将一维数组cnt改成二维,让每一行只存相同字母的连续出现次数,即只要下一个遍历到的字母跟上一个不一样,就让行号j++,并且在对应列加1,如果一样,说明是连续出现相同字母,则在当前行对应列加1。(可以把26个字母,对应为26列,从0--25。)
#include <cstdio>
#include <cstring>
char arr[110];
int cnt[110][110] = {0};
int main() {
scanf("%s", &arr);
int len = strlen(arr);
char c = ' ';
int j = 0;
for (int i = 0; i < len; i++) {
if (arr[i] != c) {
j++;
cnt[j][arr[i] - 'a']++;
c = arr[i];
}else {
cnt[j][arr[i] - 'a']++;
}
}
for (int i = 1; i <= j; i++) {
for (int m = 0; m < 26; m++) {
if (cnt[i][m] != 0) {
printf("%c %d\n", m + 'a', cnt[i][m]);
}
}
}
return 0;
}
最后发现还可以优化:
#include <cstdio>
#include <cstring>
char arr[110];
int main() {
scanf("%s", &arr);
int len = strlen(arr);
int indx = 0;
while(indx < len) {
printf("%c ", arr[indx++]);//indx++,是先用indx,后加1,此处打印的是arr[0],但打印后,indx就变为1了。
int cnt = 1;//统计相同字符连续出现的次数(每次循环都要置为1,是因为统计每一段字符的连续出现次数要从1开始计数)
while(indx < len && arr[indx] == arr[indx - 1]) {//arr[indx] == arr[indx - 1] ,与前一个字符作比较
cnt++;//累计相同字符连续出现的次数
indx++;//下标往后移,直至出现不同的字符
}
printf("%d\n", cnt);//打印arr[0]处字母连续出现的次数
}
return 0;
}