【发布时间】:2012-07-27 00:38:19
【问题描述】:
我正在动态分配内存以维护项目列表,但在尝试使用 free() 删除项目时,我收到内存堆损坏错误。而且我知道这在 C++(或 java,或任何其他面向对象的语言)中会容易得多,但我必须在 C 中执行此操作(注意:C 代码,但在 Microsoft Visual Studio 2010 中编译,并且因此是 C++ 编译器)。
这是项目“看起来”的样子:
//item.h
typedef struct
{
char* titel;
char* auteur;
int jaar;
} Boek;
typedef struct
{
enum {BOEK, TIJDSCHRIFT} itemType;
union {
Boek* boek;
Tijdschrift* tijdschrift;
} itemData;
struct Item* next;
} Item;
这是它的创建/分配方式。我还在使用strdup 和malloc/strcpy 来分配字符串之间切换,但这似乎没有任何效果。此外,我要删除的项目是 BOEK 类型,TIJDSCHRIFT allocator/deallocator 以类似的方式工作。
//item.c
Item* nieuwBoek(char* _titel, char* _auteur, int _jaar)
{
Item* item = (Item*) malloc(sizeof(Item*));
item->itemType=BOEK;
item->itemData.boek=(Boek*) malloc(sizeof(Boek*));
item->itemData.boek->titel=strdup(_titel);
item->itemData.boek->auteur=strdup(_auteur);
item->itemData.boek->jaar=_jaar;
item->next=NULL;
return item;
}
返回的指针随后被另一个函数使用,该函数将其传递给列表中前一项的item->next。
这是我试图释放它的方法。我的理解是我必须在释放结构本身之前释放分配的字符串,但即使我只是调用 free(item) (通过注释掉 deleteItem 中的其他代码或在主代码中调用它:free(nieuwBoek(...) 我收到堆损坏错误。
void deleteItem(Item* item)
{
if (item->itemType==BOEK)
{
free(item->itemData.boek->titel); // When not running in debug-mode it crashes here.
free(item->itemData.boek->auteur);
free(item->itemData.boek); // When running in debug mode it crashes here.
}
/*else if... TIJDSCHRIFT deallocator here*/
free(item);
}
并且传递给deleteItem() 的指针是指向一个项目的有效指针。它可能是我做错/失踪的一些非常愚蠢的事情,但我现在整天都被这个问题难住了,所以我向你们寻求帮助。哦,在删除项目之前,next->pointer 已设置为 NULL,因此它已经与列表断开连接,如果这很重要的话。
【问题讨论】:
-
malloc(sizeof(Boek*));应该是sizeof *boek或sizeof(Boek)(对于 item en tijdschrift 类似)verder:1)不要转换 malloc() 的返回值。 2) 不要使用带有前导下划线的标识符;它们是为实现而保留的。 -
问题是你的 malloc 的:
malloc(sizeof(Item*))。他们应该是malloc(sizeof(Item));等等... -
sizeof(Item*) 是指针的大小,而不是项目的大小....很少计划采取指针大小的操作!
标签: c pointers malloc free heap-corruption