Online Compiler C

#include <stdio.h> void pack_string(char s[]) { int time = 0; char c; for (int i = 0; s[i] != '.'; i++) { time++; c = s[i]; } int A[time], m = 0; for(int i = 0; i< time; i++) { A[i] = 1; } char B[time]; for (int i = 1; s[i] != '.'; i++) { if(s[i-1] == s[i]) { A[m]++; } else { B[m]= s[i-1]; m++; } } B[m] = c; for(int i =0 ; i < m+1; i++) { printf("%c%d", B[i], A[i]); } } int main() { return 0; }
这段代码试图实现一个字符串压缩功能,将连续重复的字符替换为“字符+重复次数”的形式,例如 "aaabb." 应输出 "a3b2"。但代码中存在逻辑错误,导致输出结果不正确。

- 第一个循环计算字符串长度(遇到 '.' 停止),但变量 time 的值比实际字符数多1,因为循环条件 s[i] != '.' 在遇到 '.' 时退出,但 time 在每次循环都增加,包括最后一次遇到 '.' 时没有增加,所以 time 等于字符数。这里没有错误,但后续使用 time 作为数组大小时需要注意。
- 第二个循环初始化数组 A 为全1,但数组 A 的大小是 time,而实际可能不需要那么多元素,因为压缩后的字符种类数可能少于 time。
- 第三个循环的逻辑有问题:它从 i=1 开始比较 s[i-1] 和 s[i],但数组 B 和 A 的索引 m 只在遇到不同字符时增加,而 A[m] 在相同字符时累加。然而,当遇到不同字符时,B[m] 被赋值为 s[i-1],但此时 A[m] 已经初始化为1,并且之前相同字符的计数已经累加在 A[m] 中。这个逻辑在连续字符段结束时正确,但第一个字符的处理有遗漏:当字符串以单个字符开始时,例如 "ab.",循环从 i=1 开始,s[0]='a', s[1]='b',不同,所以 B[0]='a', m=1,然后继续,但 s[1]='b' 与 s[2]='.' 不同,所以 B[1]='b', m=2,最后 B[m]=c 将 c(最后一个字符)赋给 B[2],但 c 是 '.',导致输出包含点号。实际上,c 在第一个循环结束时被赋值为最后一个非 '.' 字符,但这里 c 是 '.',因为循环在遇到 '.' 时停止,但 c 被赋值为 s[i] 时 i 指向 '.' 之前的字符?仔细看:第一个循环中,当 s[i] != '.' 时,c = s[i],然后 i 增加,直到 s[i] == '.' 时退出,所以 c 是最后一个非 '.' 字符。但这里字符串以