动态内存的释放

x396448534 2009-10-30 02:42:07
这是C++ primer 第四版 第137叶的一个例子

代码一:
const char *pc="a very long literal string";
const size_t len=strlen(pc);
for (size_t ix=0;ix!=1000000;++ix)
{
char *pc2=new char[len+1];
strcpy(pc2,pc);
if(strcmp(pc2,pc))
;
delete []pc2; //free the monory;
}

代码二:
string str("a very long literal string");
for (int ix=0;ix!=1000000;++ix)
{
srting str2=str;
if (str!=str)
;
//str2 is automatially feed;
}


在代码一中要释放内存 为什么用delete[];而不用delete pc2;我的问题就是delete[]和delete 用在什么时候,在看有些书上是: char *p=(char*)malloc (1000); delete p; p=0;这里delete p 不就是释放p所指向的内存空间么,还是别的,望高手指教。。。。。。。。。

是不是代码一是数组的原因。

还有代码一中为什么没把pc2=0;这样不就会出现野指针了么,还是因为pc2是for里的局部变量,在for结束会系统销毁。就跟代码二str2一样会在结束后自动销毁,我不知道会不会,请高手指教,谢谢!!!

...全文
246 21 打赏 收藏 转发到动态 举报
写回复
用AI写文章
21 条回复
切换为时间正序
请发表友善的回复…
发表回复
jubeiyaoyue_colin 2011-07-16
  • 打赏
  • 举报
回复
delete []p; //释放p及其后面的整个连续分配的空间,一般是数组
delete p; //仅释放p所指的空间,换句话说如果p是一个数组首地址的话,除第一个元素外,后面的都不会释放
zwfeng1988 2009-11-02
  • 打赏
  • 举报
回复

new 对应delete ;
new []对应delete [];
malloc 对应free;
别混用;


char *p=(char*)malloc (1000); delete p; p=0
就是说要用 free p;是不是

那为什么代码一不把p=0呢?
p=0是把指针指空,防止产生指针悬挂~
kiwigiving 2009-11-01
  • 打赏
  • 举报
回复
delete ptr 的意思是释放指针ptr所指的内存。
char *pc2=new char[len+1];
指针pc2指向的是 char[len+1]数组的首元素
如果delete pc2,只能释放首元素的内存
要想释放pc2所指的数组char[len+1]的全部内存,必须写为:delete []pc2,
意思就是释放指针pc2所指的数组的内存。

野指针的情况不会出现,指针类型对象跟int型对象一样,同样系统为它分配了一块
内存块,当该对象超出作用域时,自动释放该内存块。
pywepe 2009-11-01
  • 打赏
  • 举报
回复
看我一言中的

string是一个类,有析构函数

出{}时,生命周期结束时会调用析构,自然会把内存释放掉
CodeSpy 2009-11-01
  • 打赏
  • 举报
回复
[Quote=引用 16 楼 x396448534 的回复:]
引用 15 楼 codespy 的回复:
引用 14 楼 x396448534 的回复:
在论坛http://topic.csdn.net/t/20040717/19/3184602.html看见一个例子,这帖子的5楼,如下
#include <iostream.h> 
   
  void  main() 
  { 
  char  *p  =  new  char[100]; 
  cin.get(p,  100);//这里用getline的效果一样啊 
  cout  < <  p; 
  delete  p; 
  }

这样是不是会造成内存泄露,delete p只是销毁p[0],其他对象是不是还是没被销毁??

delete p的行为没有定义。只能delete []p。不要想继续使用p[1...99].


编译能通过啊!行为没有定义经常看见,但好像懂但又表达不出来,希望楼上兄台说下1
原来我在我贴的9#那些有说这例子,
[/Quote]
未定义就是标准里没有规定,依赖厂商的实现。
x396448534 2009-11-01
  • 打赏
  • 举报
回复
[Quote=引用 15 楼 codespy 的回复:]
引用 14 楼 x396448534 的回复:
在论坛http://topic.csdn.net/t/20040717/19/3184602.html看见一个例子,这帖子的5楼,如下
#include <iostream.h> 
   
  void  main() 
  { 
  char  *p  =  new  char[100]; 
  cin.get(p,  100);//这里用getline的效果一样啊 
  cout  < <  p; 
  delete  p; 
  }

这样是不是会造成内存泄露,delete p只是销毁p[0],其他对象是不是还是没被销毁??

delete p的行为没有定义。只能delete []p。不要想继续使用p[1...99].
[/Quote]

编译能通过啊!行为没有定义经常看见,但好像懂但又表达不出来,希望楼上兄台说下1
原来我在我贴的9#那些有说这例子,
CodeSpy 2009-11-01
  • 打赏
  • 举报
回复
[Quote=引用 14 楼 x396448534 的回复:]
在论坛http://topic.csdn.net/t/20040717/19/3184602.html看见一个例子,这帖子的5楼,如下
#include <iostream.h> 
   
  void  main() 
  { 
  char  *p  =  new  char[100]; 
  cin.get(p,  100);//这里用getline的效果一样啊 
  cout  < <  p; 
  delete  p; 
  }

这样是不是会造成内存泄露,delete p只是销毁p[0],其他对象是不是还是没被销毁??
[/Quote]
delete p的行为没有定义。只能delete []p。不要想继续使用p[1...99].
x396448534 2009-11-01
  • 打赏
  • 举报
回复
在论坛http://topic.csdn.net/t/20040717/19/3184602.html看见一个例子,这帖子的5楼,如下
#include<iostream.h>

void main()
{
char *p = new char[100];
cin.get(p, 100);//这里用getline的效果一样啊
cout << p;
delete p;
}

这样是不是会造成内存泄露,delete p只是销毁p[0],其他对象是不是还是没被销毁??
wangyang327329 2009-10-30
  • 打赏
  • 举报
回复
如果分内存时候是使用new[] ,删除的时候就要使用 delete []...;
如果是使用 new的话,就要使用delete;

但是如果指针是p = NULL 则,使用delete []p和delete p都可以
Lucifer126 2009-10-30
  • 打赏
  • 举报
回复
补充下,delete [] 是为了虚构数组的虚构函数。
Lucifer126 2009-10-30
  • 打赏
  • 举报
回复
[Quote=引用楼主 x396448534 的回复:]
在代码一中要释放内存 为什么用delete[];而不用delete pc2;我的问题就是delete[]和delete 用在什么时候,在看有些书上是: char *p=(char*)malloc (1000);  delete p; p=0;这里delete p 不就是释放p所指向的内存空间么,还是别的,望高手指教。。。。。。。。。

是不是代码一是数组的原因。

还有代码一中为什么没把pc2=0;这样不就会出现野指针了么,还是因为pc2是for里的局部变量,在for结束会系统销毁。就跟代码二str2一样会在结束后自动销毁,我不知道会不会,请高手指教,谢谢!!!


[/Quote]

其实delete[] 和delete 是效果一样的
野指针为什么不设置为NULL,因为,你下面不会在用到同一个指针了,设置不设置一样

关键是讲下delete 重载过delete[] 和delete的人应该清楚
参数就只有一个void*类型。 所以说,window 下,系统帮你记住了,之前申请了多大的空间,在哪
昵称很不好取 2009-10-30
  • 打赏
  • 举报
回复
看我的代码,如果delete []p-->delete p 这样用的话只能保证p[0]调用了析构函数,其它的p[1],p[2]……都没办法调用析构函数,导致出错
x396448534 2009-10-30
  • 打赏
  • 举报
回复
以下是网上找的,希望高手再次指点,也希望对对这个问题迷茫的人有帮助,谢谢!!


使用完动态无名变量后应该及时释放,要用到 delete 运算符
  delete p; //释放单个变量
  delete []p; //释放数组变量(不论数组是几维)
相比于一般的变量声明,使用new和delete 运算符可方便的使用变量.


带有“[]”的new和delete
  我们经常会通过new来动态创建一个数组,例如:
  char* s = new char[100];
  ……
  delete s;
  严格的说,上述代码是不正确的,因为我们在分配内存时使用的是new[],而并不是简单的new,但释放内存时却用的是delete。正确的写法是使用delete[]:
  delete[] s;
  但是,上述错误的代码似乎也能编译执行,并不会带来什么错误。事实上,new与new[]、delete与delete[]是有区别的,特别是当用来操作复杂类型时。假如针对一个我们自定义的类MyClass使用new[]:
  MyClass* p = new MyClass[10];
  上述代码的结果是在堆上分配了10个连续的MyClass实例,并且已经对它们依次调 用了构造函数,于是我们得到了10个可用的对象,这一点与Java、C#有区别的,Java、C#中这样的结果只是得到了10个null。换句话说,使用 这种写法时MyClass必须拥有不带参数的构造函数,否则会发现编译期错误,因为编译器无法调用有参数的构造函数。
  当这样构造成功后,我们可以再将其释放,释放时使用delete[]:
  delete[] p;
  当我们对动态分配的数组调用delete[]时,其行为根据所申请的变量类型会有所不 同。如果p指向简单类型,如int、char等,其结果只不过是这块内存被回收,此时使用delete[]与delete没有区别,但如果p指向的是复杂 类型,delete[]会针对动态分配得到的每个对象调用析构函数,然后再释放内存。因此,如果我们对上述分配得到的p指针直接使用delete来回收, 虽然编译期不报什么错误(因为编译器根本看不出来这个指针p是如何分配的),但在运行时(DEBUG情况下)会给出一个Debug assertion failed提示。


 此时至少要遵循以下原则:
  (1)new和delete是成对出现的。只出现一个是错误的或不规范的写法,即时能编译通过,也会有安全隐患;
  (2)使用的new与delete要相同。也就是说如果你在 new 表达式中使用了 [],你必须在对应的 delete 表达式中使用 []。如果你在 new 表达式中没有使用 [],你也不必在对应的 delete 表达式中不使用 []。
x396448534 2009-10-30
  • 打赏
  • 举报
回复
[Quote=引用 7 楼 mengde007 的回复:]
释放之后,没必要=0;有无皆可;
[/Quote]

那不会造成野指针?
mengde007 2009-10-30
  • 打赏
  • 举报
回复
释放之后,没必要=0;有无皆可;
这不是鸭头 2009-10-30
  • 打赏
  • 举报
回复
[Quote=引用 4 楼 x396448534 的回复:]
引用 2 楼 mengde007 的回复:
new 对应delete ;
new []对应delete [];
malloc 对应free;
别混用;


char *p=(char*)malloc (1000);  delete p; p=0
就是说要用 free p;是不是

那为什么代码一不把p=0呢?
[/Quote]
char *p=(char*)malloc (1000); delete p; p=0
这句写的不伦不类的...
昵称很不好取 2009-10-30
  • 打赏
  • 举报
回复
问题1见下面代码,问题2,pc2=0;应该写,但不写的话也没事,只要后面不用就可以了,但写了是好的编程习惯
#include <iostream>
#include <fstream>
#include <string>
using namespace std;

class T {
public:
T() { cout << "constructor" << endl; }
~T() { cout << "destructor" << endl; }
};

int main(){
const int NUM = 3;

T* p1 = new T[NUM];
cout << hex << p1 << endl;
// delete[] p1;
delete p1; //对于基本数据类型如int,delete和delete[]是一样的,但对于自定义类型,
//delete无法回收全部内存,楼主可以运行该程序看下,这里我把正确的写法给注释了

T* p2 = new T[NUM];
cout << p2 << endl;
delete[] p2;

return 0;
}
x396448534 2009-10-30
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 mengde007 的回复:]
new 对应delete ;
new []对应delete [];
malloc 对应free;
别混用;
[/Quote]

char *p=(char*)malloc (1000); delete p; p=0
就是说要用 free p;是不是

那为什么代码一不把p=0呢?
xingzhe2001 2009-10-30
  • 打赏
  • 举报
回复
如果你new的时候用[], delete得时候也要用[]

“在看有些书上是:
char *p=(char*)malloc (1000); delete p; p=0;

哪些书,快烧了,malloc出来的必须用free释放

pc2会自动销毁。
mengde007 2009-10-30
  • 打赏
  • 举报
回复
new 对应delete ;
new []对应delete [];
malloc 对应free;
别混用;
加载更多回复(1)

64,680

社区成员

发帖
与我相关
我的任务
社区描述
C++ 语言相关问题讨论,技术干货分享,前沿动态等
c++ 技术论坛(原bbs)
社区管理员
  • C++ 语言社区
  • encoderlee
  • paschen
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
  1. 请不要发布与C++技术无关的贴子
  2. 请不要发布与技术无关的招聘、广告的帖子
  3. 请尽可能的描述清楚你的问题,如果涉及到代码请尽可能的格式化一下

试试用AI创作助手写篇文章吧