结构体/类/指针里的成员没有正常初始化的问题

前言

今天在用C++的时候,碰到了一个比较棘手的问题——在创建结构体指针的时候指针的数据成员始终没有自动初始化,不等于我设置的默认值。即使我显式的在构造函数为其初始化,依旧没正确赋值,是随机的。显然是没有调用构造函数。

经过排查发现,通过malloc创建的对象是不会对数据成员进行初始化的,也就是说不会调用构造函数的!这是为什么呢?这要搞明白malloc及new的性质,同时搞清楚它们的区别。

解决方案:使用new操作符代替malloc创建对象

new操作符与malloc函数的区别

从对象所分配的内存空间位置上来看:new操作符为对象动态分配自由存储区(free store)上的内存空间,而malloc函数上动态分配内存。

  • 自由存储区是C++基于new操作符的一个抽象概念,凡是通过new申请到的内存,这块内存就被称为自由存储区。
  • 堆是操作系统层面上的概念,是操作系统所维护的一块特殊内存,用于程序的动态内存分配。
  • 自由存储区可以是堆,也可以不是,这取决于具体实现。(默认情况下C++编译器会使用堆来实现自由存储)

返回值类型不同:new操作符内存分配成功时,返回的是对象类型的指针,无须进行类型转换,故new是符合类型安全性的操作符。而malloc内存分配成功则是返回void* ,需要通过强制类型转换将void指针转换成我们需要的类型。

是否执行生命周期函数:new会调用对象的构造函数/析构函数完成对象的构造和析构操作;而malloc不会。这就是为什么通过malloc创建的对象是不会对数据成员进行初始化的,对其数据成员的默认值是随机的,即使指定默认值,依然是随机的。这也是两者最大的区别。

--------------------------------2023/9/22------------------------------

其实有着这些不同,主要是因为malloc是从C语言继承而来的,而new属于C++的概念。最近了解到,在C语言中并不存在构造函数的概念,因为它是结构化语言,没有对象的概念。这也就是malloc在C++中为何没有调用构造函数的本质原因了


其他:

是否重载:new操作符可以重载;而malloc是库函数,不能重载

内存分配失败时的处理策略不同: new操作符在内存分配失败时会抛出bad_alloc异常,它不会返回NULL;malloc在内存分配失败时返回NULL

内存不足时的处理方式:malloc分配的内存不足时,可以用realloc扩容;而new没有这样的配套设施

new/delete是c++中的运算符,而malloc/free是c++/c都支持的库函数.

作者:Miracle
来源:麦瑞克博客
链接:https://www.unitymake.com/archives/programming-life/cpp/2966
本博客所有文章除特别声明外,均采用CC BY-NC-SA 4.0许可协议,转载请注明!
THE END
分享
打赏
海报
结构体/类/指针里的成员没有正常初始化的问题
前言 今天在用C++的时候,碰到了一个比较棘手的问题——在创建结构体指针的时候指针的数据成员始终没有自动初始化,不等于我设置的默认值。即使我显式的在构造函……
<<上一篇
下一篇>>
文章目录
关闭
目 录