使用scanf定义动态数组大小时出现Seg fault段故障问题求助
C语言动态数组函数段错误问题排查
编写了生成结构体动态数组的函数createPkmDatabase,仅接收int类型参数taille(法语,意为size)。当taille固定为5时函数运行正常,但添加scanf("%d", &taille)手动输入数组大小后,程序出现段错误(Seg fault)。移除scanf语句后编译运行均无问题,且出错时函数内的printf语句似乎未执行,无法理解为何通过scanf修改taille值会引发该问题。
相关代码如下:
createPkmDatabase函数代码
pokemon_t * createPkmDatabase( int taille){ printf("taille %d",taille); pokemon_t *tableau=malloc(sizeof(pokemon_t)*taille); ... ... }
main函数代码
int main(){ /*"taille" means size in french */ int taille=5; printf("Saisir taille : "); scanf("%d",&taille); /* <-- BREAKS EVERYTHING */ printf("valeur de taille : %d\n ",taille); pokemon_t *database=createPkmDatabase(taille); }
问题原因分析
- 输入值非法:如果通过scanf输入了负数、0或者远超系统内存限制的超大值,会导致
malloc(sizeof(pokemon_t)*taille)出现问题。因为sizeof返回的是无符号的size_t类型,当taille为负数时,乘法运算会将其转换为极大的无符号数,malloc尝试分配远超系统可用内存的空间,直接返回NULL。后续对NULL指针的操作会触发段错误。 - 未检查malloc返回值:固定
taille=5时,malloc几乎不会失败,但手动输入时一旦malloc返回NULL,后续操作这个空指针必然引发崩溃。 - scanf输入异常:如果输入的不是有效整数(比如字母、符号),scanf会执行失败,此时
taille可能保留初始值5,但这种情况一般不会触发崩溃,所以更可能是输入了非法数值。
解决方法
- 增加输入合法性校验:在调用函数前检查
taille是否为正整数:
if (taille <= 0) { printf("Erreur : taille doit être positive\n"); return 1; }
- 检查malloc返回值:在
createPkmDatabase中添加判断,避免操作空指针:
pokemon_t *tableau=malloc(sizeof(pokemon_t)*taille); if (tableau == NULL) { perror("Erreur d'allocation mémoire"); return NULL; // 或者终止程序 }
- 校验scanf的输入结果:检查scanf的返回值是否为1,确保输入的是有效整数:
if (scanf("%d",&taille) != 1) { printf("Erreur : saisie invalide\n"); return 1; }
内容的提问来源于stack exchange,提问作者Anthony
相关产品推荐
相关产品推荐

