分段错误(核心转储)错误

时间:2011-04-28 18:32:30

标签: c segmentation-fault hashtable

我正在编写一个程序,它使用链接列表的Hashtable来计算单词的频率。程序会计算我输入的所有单词以及频率,但是在打印哈希表后,我会收到分段错误(核心转储)错误。当我对我的程序进行valgrind时,它表明我在三个不同的地方得到了大小为8的无效读取错误。我不知道如何修复它们。以下是三个不同的地方:

 void freeTable(HashTablePtr table) {
     int i;
     ListPtr list;

     if (table == NULL)
         return;

     for (i = 0; i < table->size; i++) {
         list = table->table[i];
         freeList(list);
     }

     free(table->table);
     free(table);
 }


 HashTablePtr createTable(int tableSize) {

     int i;
     HashTablePtr table = (HashTablePtr) malloc(sizeof(HashTablePtr));
     table->table = (ListPtr *) malloc(sizeof(ListPtr) * tableSize);
     table->size = tableSize;

     for (i = 0; i < table->size; i++) {
         table->table[i] = createList();
     }

     return table;
 }


 void printTable(HashTablePtr table) {

     ListPtr tempList;
     NodePtr tempNode;
     HashObjectPtr obj;
     int i;

     for (i = 1; i < table->size; i++) {
         tempList = table->table[i];
         if (tempList->size != 0) {
             tempNode = tempList->head;
             obj = tempNode->HashObject;
             printf("%s\n\n", toString(obj));
         }
     }
 }

我认为错误必须使用这些行:
tempList = table-&gt; table [i];
table-&gt; table [i] = createList();
但我不确定如何解决它。

编辑:

 typedef struct hashtable HashTable;
 typedef struct hashtable * HashTablePtr;

 struct hashtable {
     int size;
     ListPtr *table;
 };

Valgrind错误:

9个上下文中的999个错误:
== 73795 ==读取大小为8
== 73795 ==在0x400B7D:printTable(HashTable.c:96)
== 73795 == by 0x400766:main(wf.c:16)
== 73795 ==地址0x4c34048在大小为8的块之后为0字节 == 73795 ==在0x4A0515D:malloc(vg_replace_malloc.c:195)
== 73795 == by 0x400D05:createTable(HashTable.c:17)
== 73795 == by 0x400753:main(wf.c:14)
== == 73795
== == 73795
== 73795 ==上下文6中的1000错误:
== 73795 ==读取大小为8的无效 == 73795 ==在0x400B2B:freeTable(HashTable.c:128)
== 73795 == by 0x40076E:main(wf.c:17)
== 73795 ==地址0x4c34048在大小为8的块之后为0字节 == 73795 ==在0x4A0515D:malloc(vg_replace_malloc.c:195)
== 73795 == by 0x400D05:createTable(HashTable.c:17)
== 73795 == by 0x400753:main(wf.c:14)
== == 73795
== == 73795
== 73795 ==上下文7中的1000错误:
== 73795 ==读取大小为8的无效 == 73795 ==在0x400D4C:createTable(HashTable.c:25)
== 73795 == by 0x400753:main(wf.c:14)
== 73795 ==地址0x4c34048在大小为8的块之后为0字节 == 73795 ==在0x4A0515D:malloc(vg_replace_malloc.c:195)
== 73795 == by 0x400D05:createTable(HashTable.c:17)
== 73795 == by 0x400753:main(wf.c:14)

 ListPtr createList() {
     ListPtr list;
     list = (ListPtr) malloc(sizeof(List));
     list->size = 0;
     list->head = NULL;
     list->tail = NULL;
     return list;
 }

2 个答案:

答案 0 :(得分:7)

HashTablePtr table = (HashTablePtr) malloc(sizeof(HashTablePtr));几乎肯定是错的。您希望为HashTable分配足够的存储空间,但似乎您只为指向HashTable的指针(您的HashTablePtr)分配存储空间

如果你放弃了使用typedef指针的习惯,而是按照以下形式进行分配的方法,你将不会遇到这类问题:

HashTable *table = malloc(sizeof *table);

答案 1 :(得分:0)

指针的大小始终是固定大小,并且取决于体系结构。例如,在64位平台上,它总是8个字节。基本上,sizeof (ObjectType)sizeof (ObjectType *)不同。因此,在这种情况下,您最终会分配比您需要的更少的内存,从而导致分段错误。