字符串编码程序调试求助:按首类字符优先编码逻辑异常
问题排查与修正方案
你的代码在部分测试用例下运行异常,我梳理出了几个关键问题,并提供了修正后的代码:
问题分析
lower数组缺少字符串结束符
你在转换字符大小写时,仅处理了输入字符串中的有效字符,但没有给lower数组末尾添加'\0'。后续遍历lower数组时,会因找不到结束符而读取内存中的垃圾数据,导致数组越界,引发不可预测的错误。多位数无法正确转换
当连续同类字符数量超过9时(比如10个a),你的代码直接将数字加48转换为单个字符(10+48=58,对应字符:),这不符合编码规则——正确的做法是将多位数拆分为单个字符存入结果数组。最后一个字符处理逻辑错误
遍历到字符串最后一个字符时,arr[i+1]是字符串结束符'\0',你此时将'\0'赋值给结果数组,虽然printf会在第一个'\0'处停止输出,但这会占用结果数组的位置,可能导致后续操作越界,逻辑上也不合理。
修正后的代码
#include <stdio.h> #include <string.h> #define N 201 #define dif ('a'-'A') int main() { char arr[N], res[N], lower[N]; scanf("%s", arr); int len = strlen(arr); int i; // 转换为小写并添加字符串结束符 for(i = 0; i < len; i++) { if(arr[i] >= 'A' && arr[i] <= 'Z') { lower[i] = arr[i] + dif; } else { lower[i] = arr[i]; } } lower[len] = '\0'; // 关键:手动添加结束符,避免越界 int res_idx = 0; int start = 0; while(start < len) { // 保留当前同类字符的首个字符 res[res_idx++] = arr[start]; // 找到当前同类字符的结束位置 int end = start; while(end < len && lower[end] == lower[start]) { end++; } // 计算连续字符数量 int count = end - start; if(count > 1) { // 处理多位数:将数字转为字符串后拼接 char num_str[4]; // 最多200,三位数足够存储 sprintf(num_str, "%d", count); strcat(res + res_idx, num_str); res_idx += strlen(num_str); } // 移动到下一类字符的起始位置 start = end; } // 给结果数组添加结束符 res[res_idx] = '\0'; printf("%s", res); return 0; }
修正说明
- 修复
lower数组越界问题:转换完所有字符后,手动设置lower[len] = '\0',确保遍历数组时能正确识别结束位置。 - 支持多位数编码:使用
sprintf将数字转换为字符串,再拼接到结果数组中,无论数字是一位还是多位都能正确处理。 - 优化遍历逻辑:改用
while循环划分每一类字符的起始和结束位置,避免处理最后一个字符时错误引入'\0',逻辑更清晰。
测试边界情况:
- 输入
"aaaaaaaaaa"(10个a),输出"a10" - 输入
"a",输出"a" - 输入
"AaBbCc",输出"a2b2c2"
内容的提问来源于stack exchange,提问作者Prudhvi Suchendra
相关产品推荐
相关产品推荐

