实现单词错误检查代码时,加载字典到哈希表遇崩溃问题求助
问题分析与修复
你的代码运行时出现zsh: abort崩溃,核心问题集中在以下几点:
- 哈希表未初始化:全局数组
table默认是随机垃圾值,执行ptr->next = table[key];时会让新节点指向野指针,触发内存访问错误。 - 文件打开失败后未终止操作:如果
fopen返回NULL,程序仍继续执行后续的fscanf和内存操作,对空指针file读写直接引发崩溃。 - 未检查内存分配结果:
malloc可能因内存不足返回NULL,后续对ptr的操作会导致空指针异常。 - 缓冲区溢出风险:
word数组长度仅27,但字典中可能存在更长单词,fscanf("%s", word)会无限制写入,破坏栈内存引发崩溃。
具体修复步骤
初始化哈希表
在load函数开头,将table所有元素置为NULL:for (int i = 0; i < N; i++) { table[i] = NULL; }文件打开失败后立即退出
在错误分支打印提示后直接终止函数,避免后续非法操作:if (file == NULL) { cout << "无法打开字典文件" << endl; return; }检查
malloc返回值
每次分配内存后判断是否成功,失败则关闭文件并退出:struct node *ptr = (struct node *) malloc(sizeof(struct node)); if (ptr == NULL) { cout << "内存分配失败" << endl; fclose(file); return; }限制读取字符数避免溢出
修改fscanf格式符,最多读取26个字符(留1位给字符串结束符):while(fscanf(file, "%26s", word) != EOF)
完整修正代码
#include <iostream> #include <string.h> #include <cstdio> #include <ctype.h> #include <stdlib.h> #define DICTIONARY "dictionaries/large" const unsigned int N = 26; using namespace std; struct node { char word[N + 1]; struct node *next; }; struct node *table[N]; int hash_function(char *word) { int value = 0; for (int i = 0; i < strlen(word); i++) { value += tolower(word[i]); } return value % N; } void load() { // 初始化哈希表 for (int i = 0; i < N; i++) { table[i] = NULL; } FILE *file = fopen(DICTIONARY, "r"); if (file == NULL) { cout << "无法打开字典文件" << endl; return; } char word[N + 1]; // 限制读取字符数,防止缓冲区溢出 while(fscanf(file, "%26s", word) != EOF) { struct node *ptr = (struct node *) malloc(sizeof(struct node)); if (ptr == NULL) { cout << "内存分配失败" << endl; fclose(file); return; } strcpy(ptr->word, word); int key = hash_function(word); ptr->next = table[key]; table[key] = ptr; } fclose(file); // 关闭文件,避免资源泄漏 } int main() { load(); return 0; }
注:已删除重复包含的ctype.h和stdio.h头文件,减少代码冗余。
内容的提问来源于stack exchange,提问作者ASZ
相关产品推荐
相关产品推荐

