内存分配的三种方式:
1、在栈上创建。在执行函数时,函数内局部变量的存储单元在栈上创建,函数执行结束时这些存储单元会自动释放。特点:效率高、分配的容量有限
2、从堆上分配,也称为动态内存分配。程序在运行的时候用malloc或者new申请内存,并且自己利用free或delete释放内存。
3、从静态存储去分配。在编译时就分配好了内存,这块内存在程序的整个运行期间都存在。例如全局变量和静态变量。
#include<iostream>
using namespace std;
//编译时,分配地址
static int a=10;
void main()
{
int arr;
char ch;
}
malloc_free使用特点
1、malloc原型,
void *malloc(size_t size);
.注意类型转换 和 sizeof()
2、free原型,void free(void *memblock);
3、需要判断内存耗尽的问题 开辟为NULL
new_delete使用要点
1、new内置了sizeof()、类型转换 和类型安全检测,对于非内部数据类型的对象,new在创建对象时完成了初始化工作
2、new_handle机制,处理异常
malloc_free & new_delete 开辟、释放空间
#include<iostream>
using namespace std;
const int SIZE=10;
void main()
{
//动态开辟空间
int *p = (int*)malloc(sizeof(int)*SIZE);
//判断内存是否耗尽,进行处理
/*
if(p == NULL)
{
return ;
}
*/
if(p==NULL)
{
exit(1);
}
//malloc初始化
for(int i=0;i<SIZE;i++)
{
p[i]=i+1;
}
//释放
free(p);
p=NULL;
//开辟并进行初始化
char *q = new char(10);
delete(q);
q=NULL;
//通过构造函数初始化
char *s=new char[10];
delete[] s;
s=NULL;
}
C++中new_delete与malloc_free特点
1、malloc与free是标准的库函数,new与delete是c+ +的运算符。他们都可以完成动态内存的开辟和内存的释放
2、malloc与free无法满足对动态对象的要求。对象创建时要调动构造函数、消亡时自动调用析构函数,由于malloc与free是库函数不是运算符,不在编译器的控制范围,不能把构造函数和析构函数强加于构造函数和析构函数
3、new和delete正好能完成动态内存分配和初始化工作的运算符new,以及一个完成清理和释放内存的运算符delete
#include<iostream>
using namespace std;
class Test
{
public:
Test(int d=0):data(d)
{
cout<<"Create Test object"<<endl;
}
~Test()
{
cout<<"Free Test object"<<endl;
}
private:
int data;
};
void main()
{
Test *q= new Test(10);
delete(q);
q =NULL;
//1.开辟空间 2.调用构造函数
Test *s =new Test[10];
//1、调用析构函数 2.释放空间
delete[] s;
s=NULL;
}
new_delete与malloc_free实现
new :完成了Initialize() 与 malloc()的作用,即空间开辟和对象创建、初始化
delete:完成了Destroy()与free()的作用,即对象的清除与空间的释放
#include<iostream>
using namespace std;
#include<vld.h>
const int SIZE=10;
class Object
{
public:
Object(int d=0):data(d)
{
cout<<data<<"new_memory"<<endl;
}
~Object()
{
cout<<"delete_memeory!"<<endl;
}
public:
Initialize(int d)
{
data =d;
cout<<data<<"Initnalize()"<<endl;
}
Destroy()
{
cout<<"Destory()"<<endl;
}
private:
//若直接释放了空间,而没有摧毁对象,则会造成对象的内存泄露
//char *str;
int data;
};
void Use_new_delete()
{
//要有带默认值的构造函数或者缺省函数 因为数组不能直接初始化
//Object *s=new Object[10](1);
/*
Object *s=new Object[10];
delete []s;
*/
Object *q= new Object(10);
delete q;
}
void Use_malloc_free()
{
Object *p=(Object *)malloc(sizeof(Object)*SIZE);
//构造对象
p->Initialize(10);
//摧毁对象
p->Destroy();
//释放空间
free(p);
p=NULL;
}
void main()
{
//malloc_free
Use_malloc_free();
//new_delete
Use_new_delete();
}
野指针
理解:野指针不是NULL指针,是指向“垃圾”内存的指针。
原因:
1、指针么有被初始化。
char *p = NULL;
char *str=(char *)malloc(100);
2、指针被free或delete后,没有置NULL。
char *str=(char *)malloc(100);
strcpy(p,"hello");
free(p);
if(p != NULL)
//p所指内存被释放,但p所指的地址还没有改变
if(p != NULL)
//没有起到作用
{
strcpy(p,"world");//错误
}3、指针操作超越了变量的作用范围。