C语言递归打印二维数组异常排查:首行后输出错误
递归遍历二维数组的错误分析
我正在为CS50的Tideman问题练习递归,目标是用递归遍历二维数组。我写了一个3x3数组的递归打印函数,但首行打印成功后逻辑出错,后续元素输出不正确,尤其是打印i=1、j=0位置的元素时函数“失效”。以下是代码、实际输出及期望输出,请求分析错误原因:
问题代码
#include <stdio.h> void recursive_print(int lenght, int i, int j, int array[i][j]); int main(void) { int lenght = 3; int i = 0; int j = 0; int array[lenght][lenght]; array[0][0] = 0; array[0][1] = 1; array[0][2] = 2; array[1][0] = 3; array[1][1] = 4; array[1][2] = 5; array[2][0] = 6; array[2][1] = 7; array[2][2] = 8; recursive_print(lenght, i, j, array); return 0; } void recursive_print(int lenght, int i, int j, int array[i][j]) { // Base case if (i == lenght - 1 && j == lenght - 1) { printf("Base case\n"); printf("%i\n", array[i][j]); } // Recursive case(s) else if (j == lenght - 1) { printf("Recursive case 1\n"); printf("%i\n", array[i][j]); recursive_print(lenght, i + 1, j - j, array); } else { printf("Recursive case 2\n"); printf("%i\n", array[i][j]); recursive_print(lenght, i, j + 1, array); } }
实际输出
Recursive case 2 0 Recursive case 2 1 Recursive case 1 2 Recursive case 2 0 Recursive case 2 2 Recursive case 1 4 Recursive case 2 0 Recursive case 2 3 Base case 6
期望输出
Recursive case 2 0 Recursive case 2 1 Recursive case 1 2 Recursive case 2 3 Recursive case 2 4 Recursive case 1 5 Recursive case 2 6 Recursive case 2 7 Base case 8
错误原因分析
1. 二维数组参数声明错误
递归函数recursive_print的参数int array[i][j]是核心错误。C语言中,当使用变长数组(VLA)作为函数参数时,第二维的大小必须是已知的、与当前递归调用的i/j无关的固定值——你的数组是lenght x lenght的,所以参数应该声明为int array[lenght][lenght],而非用当前的i和j作为数组维度。
这个错误会导致函数对数组内存的解析完全混乱:每次递归调用时,函数会认为数组的列数是当前的j值,而非实际的3,因此访问array[i][j]时会计算出错误的内存地址,拿到完全不相关的元素值。
2. 换行时的j值初始化冗余(非核心但需优化)
在换行递归调用时,你用了j - j来得到0,虽然结果正确,但写法冗余且不直观,直接写0即可,提升代码可读性。
修正后的代码
#include <stdio.h> void recursive_print(int lenght, int i, int j, int array[lenght][lenght]); int main(void) { int lenght = 3; int i = 0; int j = 0; int array[lenght][lenght]; array[0][0] = 0; array[0][1] = 1; array[0][2] = 2; array[1][0] = 3; array[1][1] = 4; array[1][2] = 5; array[2][0] = 6; array[2][1] = 7; array[2][2] = 8; recursive_print(lenght, i, j, array); return 0; } void recursive_print(int lenght, int i, int j, int array[lenght][lenght]) { // Base case if (i == lenght - 1 && j == lenght - 1) { printf("Base case\n"); printf("%i\n", array[i][j]); return; // 加上return避免后续代码执行,可选但更严谨 } // Recursive case(s) else if (j == lenght - 1) { printf("Recursive case 1\n"); printf("%i\n", array[i][j]); recursive_print(lenght, i + 1, 0, array); } else { printf("Recursive case 2\n"); printf("%i\n", array[i][j]); recursive_print(lenght, i, j + 1, array); } }
修正后运行代码,输出将完全符合你的期望。
内容的提问来源于stack exchange,提问作者not-a
相关产品推荐
相关产品推荐

