在C ++中,我们使用delete
运算符来在大多数时间删除对象。
delete
不会使指针值为NULL。有什么方法可以自动实现吗?
EG
int *p = new int;
delete p; // this should deallocate object pointed by p
// and also initialized value of p = NULL
写这样的一个很简单:
template<class T>
void safe_delete(T*& p)
{
delete p;
p = NULL;
}
int main()
{
int* p = new int;
safe_delete(p);
double* p1 = new double;
safe_delete(p1);
}
注意不要在阵列中使用它:)
最简单的方法是覆盖运算符delete to
阅读运营商重载,是我的建议。这样,您可以保留所有当前代码,而不必经历必须将所有内容更改为函数调用。
你的建议有两个问题。
虚假的安全感
你的建议会导致虚假的安全感。当然,标准保证如果你在空指针上调用delete
,它就不会爆炸。但是,您忘记了一个小事实:没有一个指向您对象的指针。
int* p = new int(8);
int* q = p;
delete p; p = 0;
delete q; // Undefined Behavior
因此,这种做法毫无用处。而且由于虚假的安全感比没有安全感差,我实际上强烈反对它。希望人们在使用delete
nilly-willy之前会思考。
这将我们带到第二个问题
难道你不敢使用delete
delete
应该保留给智能指针或其他容器的实现者。以下适用:
*对于您正在尝试实现的目标,可能已经存在已调试的实现。
有大量现有工具来管理内存:
std::unique_ptr
或std::auto_ptr
(取决于你的C ++版本),std::scoped_ptr
,std::shared_ptr
(和它的comparse std::weak_ptr
,或者它们的boost / tr1等价物)boost::array
,boost::scoped_array
,std::vector
(和co)boost::ptr_vector
(和co)boost::intrusive_ptr
和Boost Intrusive Containers库或Boost MultiIndex库(带有BiMap衍生物)有了这样一个异类的野生动物,很难想象你突然发现了一种新的方式来使用与我们所做的完全不同的数据。如果您有,请随时发布,我们将帮助您了解如何使用这些工具来适应您的情况(或指导您如何创建新形式的智能指针)。
无论如何它都没有多大帮助,因为可能有多个指向已删除对象的指针。
int* p = new int;
int* q = p;
delete p; // how do we NULL q?
最好的想法是在p超出范围之前使用delete。或者使用标准容器,因此我们根本不需要新的/删除。
您可以编写自己的包装函数或宏来执行此操作。但是,在一般情况下很难,因为您可以将rvalues传递给delete运算符。然后应该将NULL分配给什么?
没有任何测试,我给你这个:
template <typename T> void deleteAndNull(const T*& pointer){
delete pointer;
pointer = 0;
}
可能是使用带指针的auto_ptr也可以节省您的时间。
您可以编写自己的函数来执行此操作:
void deleteAndReset (void** p)
{
delete *p;
*p = null;
}
与您的其他指针问题相同的答案 - 使用smart pointer。没有必要重新发明轮子。
这样做是非常糟糕的做法。
他们说,如果有双重删除,它会保存程序免于崩溃。唉,在删除它指向的对象后使指针为NULL,只是掩盖了问题:你的程序包含bug。
我向你保证,在这种情况下,你希望你尽可能早地和大声地崩溃。