本篇开始我们将学习C语言中没有,C++中常用的运算符new及delete。
C++57个入门知识点_22_ 构造函数和析构函数的调用时机(可手动调用构造和析构;访问权限一般为公有;局部对象声明时构造,出作用域析构;全局对象主函数前构造,出主函数后析构;全局对象实现主函数前后)中我们讲到了栈上的局部对象
和全局对象
,对象同样也是可以建在堆上的。当对象分配在堆上就被称为堆对象
。
总结:
malloc()
和free()
是C中专门用来分配和释放内存的函数,不会调用构造和析构函数;new
与delete
均为C++
中运算符,用于在堆上创建和析构对象;- 利用new与delete创建和析构对象:
new
先分配堆空间,后调用构造函数delete
先调用析构函数,后释放堆空间
//在堆上创建一个对象
CStudent* pStu=new CStudent;
//释放对象
delete pStu;
对于基本数据类型而言,new和delete仅仅分配和释放内存空间
。基本数据赋初值的写法:int* pN = new int(123);delete pN;
。
1. C语言中将对象建在堆上及释放的方法
C语言中malloc()和free()是专门用来分配和释放内存的函数,不会调用构造和析构函数
。
将对象创建在堆上的方法如下:
//C语言中在堆上分配的10个字节,如何将对象分配到堆上呢?
char* pBuf=(char*)malloc(10);
//堆对象:将对象分配到堆上,但是并没有调用对象,但是对象需要初始化和析构
CStudent* pStu = (CStudent*)malloc(sizeof(CStudent));
代码如下:
#include <iostream>
class CStudent {
public:
CStudent() {
printf("CStudent()\r\n");
//为了m_szNam创建一个堆空间(分配动态内存)
m_szName = (char*)malloc(255);
}
~CStudent() {
free(m_szName);
printf("~CStudent()\r\n");
}
void SetName(const char* pszName){}
private:
int m_nStudID;//学号
char* m_szName;
};
int main(int argc, char* argv[])
{
//C语言中在堆上分配的10个字节,如何将对象分配到堆上呢?
char* pBuf = (char*)malloc(10);
//堆对象:将对象分配到堆上,但是并没有调用对象,但是对象需要初始化和析构
CStudent* pStu = (CStudent*)malloc(sizeof(CStudent));
free(pStu);
return 0;
}
运行结果:设置内存以4字节排布,因此存在int
和char
型成员变量,堆上对象占8个字节的内存。
上面可以看到,内存的起始和结束是以“fd fd fd fd”
标志的,当修改结束的标志位为"12 fd fd fd"
,执行free()
函数进行释放时就会无法准确找到内存结束标志位
,报错如下:
上面的过程本质上是分配了一块内存,将内存对应的指针转变为CStudent
指针,因此在malloc()
的过程中并没有调用构造函数,free()
也没有调用析构。
2. 利用new与delete创建和析构对象
上面对象在堆上创建和释放使用的是malloc()
和free()
不会主动调用构造和析构,因此在C++中新建了 2个运算符new和delete来实现堆上对象的创建及析构。
#include <iostream>
class CStudent {
public:
CStudent() {
printf("CStudent()\r\n");
}
~CStudent() {
printf("~CStudent()\r\n");
}
void SetName(const char* pszName){}
private:
int m_nStudID;//学号
char* m_szName;
};
int main(int argc, char* argv[])
{
//在堆上创建一个对象
CStudent* pStu = new CStudent;
//判断对象是否为空,不为空则进行释放
if (pStu != nullptr) {
//释放指针
delete pStu;
}
return 0;
}
运行结果:
- 程序运行至
CStudent* pStu = new CStudent;
,由于已经告诉new
这是一个对象,因此会先用new给对象分配空间时,后调用构造函数
。
- 运行至
delete pStu;
就会与new相反,先调用析构函数,再释放空间
。
3. 对基本数据类型使用new和delete
对于基本数据类型而言,new和delete仅仅分配和释放内存空间
。
代码如下:
//使用new int(123)赋初值
int* pN = new int(123);
delete pN;
运行结果:
new将基本数据类型创建在堆上
delete释放堆空间
4.学习视频地址:C++57个入门知识点_25 new与delete