正确删除链表中的元素?指针的内存错误

时间:2013-10-27 16:44:09

标签: c linked-list structure valgrind

我正在实现一个具有remove_entry函数和clear_table函数的哈希表。现在我得到与remove_entry函数有关的内存读取错误。非常感谢帮助

这些是我的结构:

typedef struct bucket {
   char *key;
   void *value;
   struct bucket *next;
} Bucket;

typedef struct {
   int key_count;
   int table_size;
   void (*free_value)(void *);
   Bucket **buckets;
} Table;

这是我的功能:

int remove_entry(Table * table, const char *key){
    unsigned int hc = 0;
    Bucket *curr_b;
    Bucket *next_b;

    if(table == NULL || key == NULL){
        return FAIL;
    } else {
        hc = hash_code(key)%(table->table_size);
        if(table->buckets[hc] != NULL){
            curr_b = table->buckets[hc];

            /*Check the buckets in linked list*/
            while(curr_b != NULL){
                next_b = curr_b->next;

                if(strcmp(curr_b->key,key) == 0){
                    free(curr_b->key);
                    if(table->free_value != NULL){
                        table->free_value(curr_b->value);
                    }
                    free(curr_b);
                    curr_b = NULL;
                    table->key_count--;
                    return SUCC;
                } else {
                    curr_b = next_b;
                }
            }
            return FAIL;
        }
        return FAIL;
    }
}

删除条目后尝试读取表后会出现内存泄漏。我不认为我删除了正确的东西。

内存错误:

无法弄清楚如何从终端复制/粘贴,所以他们都说

之类的东西
Invalid read of size __
Address ____ is __ bytes inside a block of size ___ free'd

1 个答案:

答案 0 :(得分:1)

您需要考虑table->buckets[hc]是您自由的存储空间的情况。

free(curr_b->key);添加之前:

if(curr_b == table->buckets[hc]) {
    table->buckets[hc] = next_b;
}

就像现在一样,你释放了一个桶,但table->buckets[hc]仍然指向它。所以下次你读它的时候你正在阅读自由的记忆。因此错误。

此外,您需要跟踪上一个存储桶,以便在删除存储桶时将上一个存储桶指向下一个存储桶。