neu*_*ont 11 c++ memory-management
我刚刚注意到传递给的指针delete可以被const限定,而传递给它的指针free则不能.这对我来说真是一个惊喜.
在C++中,重载operator delete应具有以下签名:
void operator delete(void* p);
Run Code Online (Sandbox Code Playgroud)
但是添加一个const参数指针是无效的:
void operator delete(void const* p);
Run Code Online (Sandbox Code Playgroud)
愿有人告诉我为什么这样delete设计?
Nic*_*las 18
free不应该与实际的C++对象一起使用.free应该使用malloc,所以你不应该使用free你分配的东西new.
至于为什么你可以deleteconst对象,这很简单:
const Type *ptr = new Type(...);
Run Code Online (Sandbox Code Playgroud)
怎么办?如果你无法删除它,那么你必须这样做:
delete const_cast<Type*>(ptr);
Run Code Online (Sandbox Code Playgroud)
拥有一个对象const意味着它无法修改.您不能使对象从一个状态转到另一个状态.删除就是扔掉它.意味着它不再存在于任何状态,无论是原始状态还是其他修改形式.删除是一种存在于对象可变性状态之外的操作,就像构造一样.
从概念上讲,删除既不是const也不是非const.虽然析构函数是非const函数,但是破坏对象的想法只是在const或非const的域之外.
好的,假设您定义operator delete了一个指向const的指针(与const指针不同):
void operator delete(void const* p);
Run Code Online (Sandbox Code Playgroud)
这个功能的第一行是什么?目的operator delete是释放由分配的内存operator new.这将需要戳内存分配堆上的位.要做到这一点,你需要一个不指向const数据的指针:
void *ptr = const_cast<void*>(p);
Run Code Online (Sandbox Code Playgroud)
欢迎来到未定义的行为.虽然C++允许您这样做,但规范非常清楚,尝试写入的结果ptr(或基于它的任何地址)是未定义的.你得到了一个const指针; 外界告诉你不要修改它指向的东西.C++不保证在违反合同时会发生什么.
由于规范声明这是未定义的行为,并且由于operator delete(在大多数情况下)在不修改指向的内存p(或基于该地址修改内存)的情况下无法完成其工作,因此规范的愚蠢将允许您定义operator delete这种方式.它基本上会将自己在脚下拍摄的想法册封.
是的,几乎在所有情况下,这都是完全安全的.但是既然你无论如何都要抛弃const,为什么甚至懒得在一开始就让这个相当可疑的想法呢?
free是C函数.它的签名是20 - 30年,从没有constC语言的时代开始(并且没有C++语言).C++编译器free像其他所有函数一样对待,并且不能让它接受const没有free强制转换的指针,因为它可能会改变指向的对象.实际上,它确实如此delete,但C++并不知道它free用于内存管理.
| 归档时间: |
|
| 查看次数: |
5740 次 |
| 最近记录: |