这样delete 内存能被回收吗?

sgch2010 2011-05-27 03:46:33
char* buf;
CTest* p = new CTest();
buf = (char*)p;
delete buf;
...全文
304 37 打赏 收藏 转发到动态 举报
写回复
用AI写文章
37 条回复
切换为时间正序
请发表友善的回复…
发表回复
QQ515311445 2011-06-02
  • 打赏
  • 举报
回复
[Quote=引用楼主 sgch2010 的回复:]
char* buf;
CTest* p = new CTest();
buf = (char*)p;
delete buf;
[/Quote]
可以,但是你不能再调用delete p;了否则可能会出现异常
toadzw 2011-06-02
  • 打赏
  • 举报
回复
不能,你的P是char型,转换以后释放,系统只会按照char的大小去释放;
pathuang68 2011-06-02
  • 打赏
  • 举报
回复
[Quote=引用 3 楼 pengzhixi 的回复:]

你这么做就是个错误,本来需要调用析构函数的,你这样一改就不可能调用了。new和delete时指针的类型应该是一致的。
[/Quote]

++
正解。

唯一的例外(也可以不认为是例外),比如:

#include <iostream>
using namespace std;

class B
{
public:
virtual ~B()
{
cout << "~Btor" << endl;
}
};

class A : public B
{
public:
~A()
{
cout << "~Ator" << endl;
}
};

int main(int argc, char** argv)
{
A* a = new A;
B* b = a;
delete b;

return 0;
}

这样是可以正确释放内存的。但条件是:
1. A和B有继承关系,即A和B可以进行某种程度的类型转换
2. 上面给出的示例代码是向上转型的(upcasting),因此是安全的;如果反过来向下转型,则未必安全
3. 楼主给出的char和CTest没有上面要求的两种特性,因此一定会存在问题。
herry-Li 2011-06-02
  • 打赏
  • 举报
回复
这样做可以释放已new的内存块,但同时也失去了操作系统自动调用析构函数的机会。如果你在析构函数中有内存释放(如:delete,free等)操作的话,也可能造成操作;还有如果你在析构函数里做了一些应用方面的处理,用这种方式方式也是很危险的。当然这都是你应用的问题,和操作系统无关。
blueice2004 2011-06-02
  • 打赏
  • 举报
回复
kankan
woncomp 2011-06-02
  • 打赏
  • 举报
回复
学习了
辰岡墨竹 2011-06-02
  • 打赏
  • 举报
回复
[Quote=引用 30 楼 mougaidong 的回复:]

引用 27 楼 luciferisnotsatan 的回复:
可以。
分配的大小,系统会在某处记录。而不是看delete那个指针的类型。

请问记录在哪儿?能给讲讲嘛
[/Quote]
比如Windows里new/delete是调用HeapAlloc、HeapFree等堆函数管理内存的,堆内部实现了一个结构来记录每个对象的大小,这个记录不是在C++语言机制里的。
但是这种行为是和实现相关的。
还是那句:If not, the behavior is undefined.这是未定义行为,可能存在内存泄漏的危险。
turing-complete 2011-06-02
  • 打赏
  • 举报
回复
[Quote=引用 27 楼 luciferisnotsatan 的回复:]
可以。
分配的大小,系统会在某处记录。而不是看delete那个指针的类型。
[/Quote]

请问记录在哪儿?能给讲讲嘛
Saingel 2011-06-01
  • 打赏
  • 举报
回复
部分回收
turing-complete 2011-06-01
  • 打赏
  • 举报
回复
[Quote=引用 17 楼 pengzhixi 的回复:]
If not, the behavior is undefined. [Note: this means that the syntax of the delete-expression must match the type of the object allocated by new, not the syntax of the new-expression. ]

直接上标准,根本就没必……
[/Quote]

++ ,依赖于各公司的吧编译器了,这样
luciferisnotsatan 2011-06-01
  • 打赏
  • 举报
回复
可以。
分配的大小,系统会在某处记录。而不是看delete那个指针的类型。
天外来客-007 2011-06-01
  • 打赏
  • 举报
回复
可以释放p指向的内存,但是不能释放CTest在创建p时分配的内存,易造成内存泄露。
当然,如果CTest本身没有分配内存,则没有问题!
  • 打赏
  • 举报
回复
[Quote=引用 24 楼 sgch2010 的回复:]

哦,谢谢大家的回复,我试过了 在linux 里是不会内存泄露的,
我忘记说明了
其实我的CTest就是一个结构体,大概是这样的:
class CTest
{
public:
int a;
int b;
int c;
};
CTest * pTest = new CTest();
char *pBuf = (char*)pTest;
delete pBuf……
[/Quote]

一般编译器的做法会在某个地方(可能是头部)记下当初new分配的大小,delete的时候根据该大小进行释放
所以你用结构一般不会造成内存泄露
但是这种做法失去了指针的类型,也就不能调用析构函数了,如果析构函数什么事也没做,就凑合着运行了
sgch2010 2011-06-01
  • 打赏
  • 举报
回复
哦,谢谢大家的回复,我试过了 在linux 里是不会内存泄露的,
我忘记说明了
其实我的CTest就是一个结构体,大概是这样的:
class CTest
{
public:
int a;
int b;
int c;
};
CTest * pTest = new CTest();
char *pBuf = (char*)pTest;
delete pBuf;
是能回收12个字节的,但是我不知道原理是啥。
Julykey 2011-05-27
  • 打赏
  • 举报
回复
我感觉9楼的方法好,

char* buf;
CTest* p = new CTest();
buf = (char*)p;
buf = NULL;
delete p;
tompaz 2011-05-27
  • 打赏
  • 举报
回复
[Quote=引用 17 楼 pengzhixi 的回复:]

If not, the behavior is undefined. [Note: this means that the syntax of the delete-expression must match the type of the object allocated by new, not the syntax of the new-expression. ]

直接上标准,根本就没……
[/Quote]
这标准从哪里看的?
求指教
chengzhe 2011-05-27
  • 打赏
  • 举报
回复
显然能够被回收! 操作系统不会考虑类型的

这样做的遗憾是不能调用析构函数了
nicknide 2011-05-27
  • 打赏
  • 举报
回复
[Quote=引用 15 楼 kingbird_wang 的回复:]
显然是释放一个字节.
[/Quote]
标准库函数的话, 很明显是原始内存的长度大小。
跟类型无关。
xspace_time 2011-05-27
  • 打赏
  • 举报
回复
要遵守语法规则,不然很容易出错的,改下写法会比较好
char* buf;
CTest* p = new CTest();
buf = (char*)p;
delete p

程序员使用new在堆上申请内存,需要自己动手释放
buf属于编译器申请的内存,应该由编译器来释放

声名Ctest类指针p
调用指针函数new申请一块CTest()类内存
使用p指向new指针申请的内存
new函数所在类调用解析函数释放new指针
内存申请完成
MewX 2011-05-27
  • 打赏
  • 举报
回复
[Quote=引用 1 楼 bdmh 的回复:]

谈不上回收,只是告诉系统,这块内存可以再次被分配了
[/Quote]
[Quote=引用 3 楼 pengzhixi 的回复:]

你这么做就是个错误,本来需要调用析构函数的,你这样一改就不可能调用了。new和delete时指针的类型应该是一致的。
[/Quote]
Right!
加载更多回复(17)

64,266

社区成员

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

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