C语言统计字符串最高频元素时二维数组出现垃圾值问题求助
问题描述
- 实现目标:查找字符串中出现频率最高的元素
- 原实现思路:将字符串的单个字符转换为对应整型值存入int数组,对int数组排序后统计各字符出现频次
- 故障现象:使用二维数组
x存储统计结果,其中x[0][y]存储具体数值,x[1][y]存储对应数值的出现频率,运行时二维数组内出现无意义垃圾值
注:提问者说明自身英语水平有限,敬请谅解
问题复现代码
#include<stdio.h> #include<time.h> #include<math.h> #include<string.h> #include<conio.h> #include<ctype.h> #include<stdlib.h> #include<malloc.h> void bubble(int a[],int x); void frequenza(int A[], int n); int main(){ size_t counter; char a[] = "asrfujefwaa"; int b[20]; int x; x = strlen(a); for(counter = 0; counter != strlen(a); counter ++) { b[counter] = a[counter]; } bubble(b,x); for(counter = 0; counter != x; counter ++) { printf("%d ",b[counter]); } puts("\n"); system("pause"); puts("\n"); frequenza(b,x); return 0; } void bubble(int a[],int x) { size_t i; int ord; int scambio; scambio = 0; if(ord == 1) { return; } else { ord = 1; for(i = 0; i < x - 1; i++) { if(a[i] > a[i + 1]) { scambio = a[i]; a[i] = a[i + 1]; a[i + 1] = scambio; ord = 0; } } bubble(a,x); } } void frequenza(int A[], int n) { int x[2][n]; int z = 0; int y = 0; size_t q; x[0][0] = A[0]; x[1][0] = 1; for(z = 0; z != n; z++) { if(x[0][y] == A[z + 1]) { x[1][y] += 1; } if(x[0][y] != A[z + 1]) { y++; x[0][y] = A[z + 1]; } } for(z = 0; z != 2; z++) { puts("\n"); for(q = 0; q != y;q++) { printf("%d ",x[z][q]); } } }
故障排查结果
代码共有3处直接导致垃圾值的bug:
- 冒泡排序函数存在未初始化变量问题
bubble函数中局部变量ord声明后未赋初始值,就直接执行if(ord == 1)的判断,属于C语言未定义行为,大概率第一次进入函数就直接触发return,根本没有执行排序逻辑,传入频次统计函数的数组是乱序的。 - 频次统计函数存在数组越界访问
frequenza的循环条件为z从0到n-1,循环内访问A[z+1]时,当z=n-1会访问到A[n],超出数组合法下标范围(合法下标为0~n-1),读到栈上的随机垃圾值。 - 频次统计逻辑未初始化新条目计数值
栈上创建的可变长度数组x[2][n]不会自动初始化为0,当检测到新字符、执行y++切换到新统计条目时,仅给x[0][y]赋值了字符数值,没有给对应的计数位x[1][y]设置初始值1,后续累加计数是在栈上原有垃圾值的基础上计算,直接输出无意义数字;同时打印循环的终止条件为q != y,会漏掉最后一个统计条目的输出。
修复要点
- 给
bubble函数的ord变量赋初始值0,保证排序逻辑正常执行 - 调整
frequenza的循环边界为z < n-1,避免数组越界 - 新增统计条目时,同步给对应计数位
x[1][y]赋初始值1 - 调整打印循环的终止条件为
q <= y,保证所有统计条目都能输出
内容的提问来源于stack exchange,提问作者steno
相关产品推荐
相关产品推荐

