代码执行完ColocaCandidatos函数后终止,无法执行后续代码的问题求助
代码执行完ColocaCandidatos函数后终止,无法执行后续代码的问题求助
我写了一段C代码,本来要读取CSV文件内容,把数据整理到结构体数组里同时打印读取结果,但现在程序跑完ColocaCandidatos函数后就直接终止了,后面的测试代码(比如x、y、z的计算和打印)完全没机会执行。我特意加了测试变量排查,但还是找不到问题所在,有没有大佬能帮忙看看?
我的代码如下:
#include <stdio.h> #include <stdlib.h> #include <string.h> typedef struct{ int StudentID; float ProvaIngresso; float NotaSecundario; float NotaCandidatura; int Escolha1, Escolha2, Escolha3, Escolha4, Escolha5; char curso1[4], curso2[4], curso3[4], curso4[4], curso5[4]; }Candidato; void ColocaCandidatos(Candidato *candidatos); int main() { Candidato candidatos[60000]; ColocaCandidatos(&candidatos[60000]); int x = 1; int y = 2; int z = x +y; printf("%d",z); return 0; } void ColocaCandidatos(Candidato *candidatos){ FILE *fp; char line[100]; char *token; int line_count = 0; int i= 0; //token pa controlar numero do candidato; // Open the CSV file for reading fp = fopen("Candidatos_N10_C20_O05.csv", "r"); if (fp == NULL) { printf("Error: could not open file\n"); exit(1); } // Read each line of the file and extract the string while (fgets(line, 100, fp) != NULL) { if (line_count > 0) { // Skip the first line token = strtok(line, ","); candidatos[i].StudentID = atoi(token); printf("\n%d",candidatos[i].StudentID); token = strtok(NULL, ","); candidatos[i].ProvaIngresso = atof(token); printf("\n%f",candidatos[i].ProvaIngresso); token = strtok(NULL, ","); candidatos[i].NotaSecundario = atof(token); printf("\n%f",candidatos[i].NotaSecundario); token = strtok(NULL, ","); candidatos[i].NotaCandidatura = atof(token); printf("\n%f",candidatos[i].NotaCandidatura); token = strtok(NULL, ","); candidatos[i].Escolha1 = atoi(token); printf("\n%d",candidatos[i].Escolha1); token = strtok(NULL, ","); strcpy(candidatos[i].curso1,token); printf("\n%s",candidatos[i].curso1); token = strtok(NULL, ","); candidatos[i].Escolha2 = atoi(token); printf("\n%d",candidatos[i].Escolha2); token = strtok(NULL, ","); strcpy(candidatos[i].curso2,token); printf("\n%s",candidatos[i].curso2); token = strtok(NULL, ","); candidatos[i].Escolha3 = atoi(token); printf("\n%d",candidatos[i].Escolha3); token = strtok(NULL, ","); strcpy(candidatos[i].curso3,token); printf("\n%s",candidatos[i].curso3); token = strtok(NULL, ","); candidatos[i].Escolha4 = atoi(token); printf("\n%d",candidatos[i].Escolha4); token = strtok(NULL, ","); strcpy(candidatos[i].curso4,token); printf("\n%s",candidatos[i].curso4); token = strtok(NULL, ","); candidatos[i].Escolha5 = atoi(token); printf("\n%d",candidatos[i].Escolha5); token = strtok(NULL, ","); strcpy(candidatos[i].curso5,token); printf("\n%s",candidatos[i].curso5); i++; } line_count++; } }
问题分析
你代码里的致命错误出在main函数的这一行:
ColocaCandidatos(&candidatos[60000]);
candidatos是一个大小为60000的数组,它的合法下标范围是0到59999,candidatos[60000]已经超出了数组的内存边界,属于越界访问。
当你把这个越界的地址传给ColocaCandidatos函数后,函数里对candidatos[i]的赋值操作会覆盖栈上的关键数据(比如main函数的返回地址、栈帧的控制信息)。等函数执行完准备返回时,程序找不到正确的返回位置,直接崩溃终止,自然就跑不到后面的x、y、z计算和printf代码了。
解决方案
- 修正函数调用的传参
把调用改成下面两种写法的任意一种都可以:
// 写法1:数组名本身就是指向第一个元素的指针 ColocaCandidatos(candidatos); // 写法2:显式传第一个元素的地址 ColocaCandidatos(&candidatos[0]);
这样传参才是正确的,指向结构体数组的起始位置,后续的赋值操作都会在合法的内存范围内进行。
- 补充几个优化/修复点
- 记得在函数结束前关闭文件,避免资源泄漏:在
while循环结束后加上fclose(fp); - 60000个结构体在栈上分配可能导致栈溢出(栈空间一般只有几MB),建议用动态内存分配:
int main() { // 动态分配内存 Candidato *candidatos = malloc(60000 * sizeof(Candidato)); if (candidatos == NULL) { printf("内存分配失败\n"); return 1; } ColocaCandidatos(candidatos); // ... 后续代码 ... // 用完记得释放内存 free(candidatos); return 0; } fgets读取的行末尾会带有换行符\n,可能影响strtok的解析,建议在处理前去掉换行符:while (fgets(line, 100, fp) != NULL) { // 去掉末尾的换行符 line[strcspn(line, "\n")] = '\0'; if (line_count > 0) { // ... 原有解析代码 ... } line_count++; }
备注:内容来源于stack exchange,提问作者Difrox
相关产品推荐
相关产品推荐

