C语言骑士路径遍历程序调用printf后链表数据不可读问题求助
问题根本原因
- 核心错误:返回了栈内存的指针
你在findKnightPathCoveringAllBoard函数中定义的chessPosList lst是栈上的局部变量,函数运行期间栈内存有效,所以你调试时看到函数执行完数据是正常的。但函数返回后,该函数的栈帧会被系统回收,后续调用其他函数(比如你此处的printf)时,新的函数栈帧会直接覆盖这块内存区域,原来存储的链表数据自然就变成了不可读的垃圾值。 - 次要隐患:野指针写入
你在sectionOperator中定义的char* file仅声明了指针,没有分配对应的内存空间,后续执行scanf("%s", file)时会直接向野指针指向的未知内存写入数据,会触发未定义行为,轻则污染其他内存数据,重则直接导致程序崩溃。
修复方案
- 修复栈指针返回问题:将链表改为堆上动态分配
修改findKnightPathCoveringAllBoard函数,将局部栈上的链表改为malloc动态分配:
chessPosList* findKnightPathCoveringAllBoard(pathTree *path_tree) { // 改为堆上分配内存,生命周期不随函数结束而结束 chessPosList *lst = (chessPosList*)malloc(sizeof(chessPosList)); chessPosArray* visited; createEmptyList(lst); visited = (chessPosArray*)malloc(sizeof(chessPosArray)); checkMemoryFail(visited); visited->size = 0; if (findPathRec(path_tree->root,visited)) { createPathList(lst,visited); return lst; } else { free(lst); // 没找到路径要提前释放避免泄漏 free(visited); return NULL; } }
链表使用完毕后记得手动调用free释放,避免内存泄漏。
2. 修复野指针问题:给文件名存储分配空间
修改sectionOperator中的文件名字段,要么直接定义为栈数组,要么动态分配内存:
// 方案1:直接用栈数组,无需手动释放 char file[256]; // 方案2:动态分配,用完释放 // char* file = (char*)malloc(256 * sizeof(char));
内容的提问来源于stack exchange,提问作者SiiilverSurfer
相关产品推荐
相关产品推荐

