c中使用malloc出现的问题
- 程序员必须确定对象的长度
- malloc 返回一个
(void *)
指针 ,c++不允许将(void*)
赋值给其它指针,必须强转 - malloc可能申请内存失败,所以必须判断返回值来保存内存分配成功
- 用户在使用对象之前必须记住对他初始化,构造函数不能显示调用初始化(构造函数是由编译器调用的),用户有可能忘记调用初始化函数
c的动态内存分配函数太复杂,容易令人混淆,是不可接受的,c++中我们推荐使用运算符new和delete
new运算符和delete运算符
-
Person *p=new Person
会返回一个Person -
默认调用析构函数,开辟空间,返回不是
void*
,不需要强制转换 -
delete释放
-
new对象用
void *
取接受,释放不了对象 -
new出来的是数组,如何释放 ? delete[]
-
new出来的是数组,肯定会调用默认构造
#include<iostream>using namespace std;class Person{public:Person(){cout << "默认构造函数调用" << endl;}Person(int a){cout << "有参构造调用" << endl;}~Person(){cout << "析构函数调用" << endl;}};void test01(){//Person p1; //栈区开辟Person *p2 = new Person;//堆区开辟//所有new出来的对象,都会返回该类型的指针//malloc返回void*还要强转//malloc会调用构造吗?不会 new会调用构造//new运算符,malloc是函数//释放堆区域的空间//delete也是运算符,要配合new用,malloc配合free用delete p2;}void test02(){void *p = new Person;//当用void* 接受new出来的指针,会出现释放的问题delete p;//无法释放p}void test03(){//同过new来开辟数组//一定会调用默认构造函数,所以一定要提供默认构造Person *pArray = new Person[10];//Person pArray2[2] = { Person(1), Person(2) };//在栈上开辟数组,可以指定有参构造//释放数组 delete[]必须加上中括号delete []pArray;}int main(){//test01();//test02();test03();system("pause");return 0;}
malloc/free和new/delete的区别
malloc/free和new/delete的共同点是:都是从堆上申请空间,并且需要用户手动释放。不同的地方是:
- malloc和free是函数,new和delete是操作符
- malloc申请的空间不会初始化,new可以初始化
- malloc申请空间时,需要手动计算空间大小并传递,new只需在其后跟上空间的类型即可
- malloc的返回值为void*, 在使用时必须强转,new不需要,因为new后跟的是空间的类型
- malloc申请空间失败时,返回的是NULL,因此使用时必须判空,new不需要,但是new需要捕获异常
- 申请自定义类型对象时,malloc/free只会开辟空间,不会调用构造函数与析构函数,而new在申请空间 后会调用构造函数完成对象的初始化,delete在释放空间前会调用析构函数完成空间中资源的清理
- new/delete比malloc和free的效率稍微低点,因为new/delete的底层封装了malloc/free