malloc、struct、std::string 和 free 可能存在内存泄漏
我遇到如下情况,我不确定结构体的 std::string 元素是否泄漏内存,或者这是否可以。当调用 free(v) 时,这两个 std::string 分配的内存是否被删除?
struct MyData
{
std::string s1;
std::string s2;
};
void* v = malloc(sizeof(MyData));
……
MyData* d = static_cast<MyData*>(v);
d->s1 = "asdf";
d->s2 = "1234";
?
free(v);
漏不漏
我使用 void 指针是因为我有另一个高级结构,它由枚举和 void 指针组成。根据枚举变量的值,void* 将指向不同的数据结构。
示例:
枚举字段有 EnumValue01 => void-pointer 将指向 malloc'd MyData01 struct
enum-field has EnumValue02 =>; void-pointer 将指向 malloc'd MyData02 struct
当然,非常感谢针对不同方法的建议。
I've a situation like the following, and I'm not sure whether or not the std::string elements of the struct leak memory or if this is ok. Is the memory allocated by those two std::strings deleted when free(v)
is called?
struct MyData
{
std::string s1;
std::string s2;
};
void* v = malloc(sizeof(MyData));
...
MyData* d = static_cast<MyData*>(v);
d->s1 = "asdf";
d->s2 = "1234";
...
free(v);
Leak or not?
I'm using the void-pointer because I have another superior struct, which consists of an enum and a void-pointer. Depending on the value of the enum-variable, the void* will point to different data-structs.
Example:
enum-field has EnumValue01 => void-pointer will point to a malloc'd MyData01 struct
enum-field has EnumValue02 => void-pointer will point to a malloc'd MyData02 struct
Suggestions for different approaches are very appreciated, of course.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(6)
您不应该在 C++ 程序中使用
malloc()
和free()
;他们不了解构造函数/析构函数。使用
new
和delete
运算符。You shouldn't be using
malloc()
andfree()
in a C++ program; they're not constructor/destructor-aware.Use the
new
anddelete
operators.这是未定义的行为 - 由
malloc()
分配的内存未初始化,因此将其用作包含string
对象的结构可能会导致任何结果;我预计会崩溃。由于在调用free()
之前没有人调用析构函数,因此string
对象不会被销毁,并且它们的缓冲区几乎肯定会泄漏。That's undefined behavior - memory allocated by
malloc()
in uninitialized, so using it as a struct containingstring
objects can lead to anything; I'd expect crashing. Since no-one invokes the destructor before callingfree()
,string
objects won't be destroyed and their buffers will almost definitely leak.确实有泄漏。 free 不会调用 MyData 析构函数(毕竟它是一个 C 函数,对 C++ 的东西一无所知)。要么你应该使用 new/delete 而不是 malloc/free:
要么自己调用析构函数:
正如 Sharptooth 指出的那样,你不能直接使用 malloc 分配的内存作为 MyData 结构而不进行初始化,所以你也必须自己这样做。要使用已分配的内存初始化 MyData,您需要使用placement new(请参见上面的代码)。
There is a leak indeed. free doesn't call MyData destructor (after all it's a C function which doesn't know anything about C++ stuff). Either you should use new/delete instead of malloc/free:
or call destructor by yourself:
as sharptooth noted you can't directly use memory allocated by malloc as a MyData struct without initialization, so you have to do it by yourself as well. To initialize MyData using already allocated memory you need to use placement new (see in the code above).
是的,因为构造函数和析构函数没有被调用。使用
新建
和删除
。Yes, because the constructor and destructor are not called. Use
new
anddelete
.即使您设法正确初始化 s1 和 s2,仅执行 free(d) 也不会回收为 s1 和 s2 动态分配的任何内存。您确实应该通过 new 创建 *d 并通过 delete 销毁,这将确保 s1 和 s2 的正确销毁(以及初始化)。
Even if you manage to initialize s1 and s2 properly, simply doing free(d) won't reclaim any memory dynamically allocated for s1 and s2. You should really create *d through new and destroy through delete, which will ensure proper destruction of s1 and s2 (and initialization as well).
是的,您可能正在泄漏,并且您的字符串也没有正确构造。程序的行为是未定义的,这意味着一切都会出错。
完成您正在做的事情最接近的有效方法是放置
new
。尽管如此,使用一些公共基类和适当的 C++ 多态性会更好。如果可能的类型不相关,您可以使用 Boost.Any 或 Boost.Variant。
Yes, you are probably leaking, and your strings aren't properly constructed, either. The program's behaviour is undefined, meaning everything is going to go wrong.
The closest valid way to do what you're doing is placement
new
. Still, you'd be better off with some common base class and proper C++ polymorphism.If the possible types are unrelated, you can use Boost.Any or Boost.Variant.