【发布时间】:2013-12-13 08:28:18
【问题描述】:
我已经创建了一个基于Simple Object System 的简单对象系统。然后我决定通过添加一个函数来扩充代码,以便在怪物死亡时释放所有关于怪物的内存:
void Monster_destroy(void *self)
{
Monster* monster=self;
if(&(monster->proto))
free(&(monster->proto));
free(monster);
}
我在这里使用的函数是这样的:
int Monster_attack(void* self,int damage)
{
Monster* monster=self;
char* desc=monster->proto.description;
printf("You attack %s!\n", desc);
monster->hit_points-=damage;
if(monster->hit_points>0)
{
printf("It is still alive\n");
return 0;
}
else
{
printf("It is dead\n");
monster->proto.destroy(monster);
return 1;
}
}
我收到以下错误:
==4699== Invalid free() / delete / delete[] / realloc()
==4699== at 0x4C2B83A: free (vg_replace_malloc.c:468)
==4699== by 0x40080F: Monster_destroy (ex19.c:15)
==4699== by 0x400A2C: Room_attack (ex19.c:96)
==4699== by 0x400ACA: Map_attack (ex19.c:118)
==4699== by 0x400E20: process_input (ex19.c:175)
==4699== by 0x400F52: main (ex19.c:211)
==4699== Address 0x51fd500 is 0 bytes inside a block of size 56 free'd
==4699== at 0x4C2B83A: free (vg_replace_malloc.c:468)
==4699== by 0x400803: Monster_destroy (ex19.c:14)
==4699== by 0x400A2C: Room_attack (ex19.c:96)
==4699== by 0x400ACA: Map_attack (ex19.c:118)
==4699== by 0x400E20: process_input (ex19.c:175)
==4699== by 0x400F52: main (ex19.c:211)
==4699==
我有一个怪物看起来像这样的系统:
struct Monster
{
Object proto;
int hit_points;
};
typedef struct Monster Monster;
Object 是一个看起来像这样的结构:
typedef struct
{
char *description;
int (*init)(void *self);
void (*describe)(void* self);
void (*destroy)(void* self);
void* (*move)(void* self,Direction direction);
int (*attack)(void* self,int damage);
}Object;
这就是我现在使用 `Monster_destroy 的方式:
if(monster && monster->hit_points>0)
{
monster->proto.attack(monster,damage);
return 1;
}
else
{
//dont even call Monster_attack because Monster has no hit_points
printf("You flail at the air and hit nothing,Idiot\n");
if(monster)
monster->proto.destroy(monster);
return 0;
}
【问题讨论】:
-
我觉得最后这个free(monster)没什么用,因为它只是栈上的一个指针(你没有在堆上分配)。
-
虽然关于您发布的代码的答案听起来是正确的,但我想指出一个事实,即 Valgrind 显示的调用堆栈与
Monster_attack无关,尽管有 @987654330 @。你确定你有正确的功能吗? -
哦,等等,我将 Monster_destroy 的调用从 Monster_attack 更改为 Room_attack,因为我想看看它是否在那里工作。
标签: c struct function-pointers free