当类没有析构函数时,智能指针或作用域指针会删除对象吗
Posted
技术标签:
【中文标题】当类没有析构函数时,智能指针或作用域指针会删除对象吗【英文标题】:Will the smart pointer or scoped pointers delete an object when the class has no destructor 【发布时间】:2012-02-24 07:28:04 【问题描述】:当类没有析构函数时,智能指针或作用域指针是否会删除对象 如果没有,为什么不离开范围,让对象自己删除呢?
【问题讨论】:
“被自己删除”是什么意思? 如果没有明确编写析构函数,C++ 将为您创建一个默认析构函数。所以智能指针总会有一个析构函数可以调用。 【参考方案1】:删除实例时,即使您没有析构函数,也会删除所有类成员。处理指针时会发生内存泄漏:
class A
private:
B* b;
;
在这种情况下,b
本身会在A
的实例被删除时被销毁,但它指向的内存不会。
class A
private:
SmartPtr<B> b;
;
在智能指针的情况下,通常在析构函数中有一些引用计数和内存清理,它指向的内存会被它的析构函数显式销毁,而智能指针的析构函数会在实例时被隐式调用包含的类被销毁。
【讨论】:
【参考方案2】:是的。这就是智能指针的用途。 http://www.boost.org/doc/libs/1_48_0/libs/smart_ptr/smart_ptr.htm
http://en.wikipedia.org/wiki/Smart_pointer
What is a smart pointer and when should I use one?
【讨论】:
【参考方案3】:是的,无论类是否具有析构函数,智能指针都会删除对象。请注意,智能指针用于堆上分配的对象(使用new
),并且这些对象在超出范围时不会释放内存,您需要显式地delete
它们。智能指针将移除显式删除它们的过程。
【讨论】:
【参考方案4】:指向对象本身的指针将被删除。但是,如果类中有任何动态分配的数据,它将不会被释放。拥有析构函数的想法是能够对类对象进行后处理,主要是释放所占用的任何资源。
【讨论】:
【参考方案5】:new 和 delete 做两件事。
new
分配内存并获取一个对象以在该内存空间中构造自己。
delete
先让对象自毁,然后释放内存。
请注意,可以为某些智能指针提供自定义删除器,该删除器不会在对象上调用 delete,但无论您要求它做什么。有时您可能希望将其传递为空操作。
【讨论】:
【参考方案6】:你的观点很好;智能指针的用途并不多
在 C++ 中,因为大多数时候它们可能是相关的,所以你会
最好使用值语义和复制。如果是
scoped_ptr
,最常使用的是实际对象为
多态:
scoped_ptr<Base> pObj = condition
? static_cast<Base*>( new Derived1 )
: static_cast<Base*>( new Derived2 );
(很遗憾,至少需要static_cast
之一。)
如果您要处理多态对象的容器,则需要
shared_ptr
相反,如果您要返回多态对象,或者
否则传递它,如果可以的话,你将使用unique_ptr
保证它的可用性,否则auto_ptr
——在某些情况下
在你传递它的地方,shared_ptr
可能更合适。
在返回或传递对象的情况下,成本 复制它也可能是使用智能指针的动机,即使 对象不是多态的。在这种情况下,我仍然会使用值语义 (即复制和分配对象本身)除非我有 性能问题。
请注意,智能指针不仅仅用于内存管理。一世
线程间队列接口中经常使用auto_ptr
:
一旦对象被插入到队列中,它就不再属于
到发送线程; auto_ptr
准确地表达了这些语义,
发送线程中的auto_ptr
变得无效。或者一个
可修改的单例(应该非常非常罕见的东西)可能
在其instance
函数中获取锁,并返回shared_ptr
它释放了最终析构函数中的锁。我也用过smart
一种或两种情况下的指针以确保事务语义:在一种情况下
例如,对象位于许多不同的集合中(其中
当然,持有指向它们的指针),根据不同的排序
标准。要修改一个对象,你需要一个指向它的共享指针;这
返回此共享指针的函数也删除了对象
从集合中,以便您也可以安全地修改键值,
最后的析构函数根据
新钥匙。等等——smart 有很多用途
与内存管理或对象无关的指针
终生。
【讨论】:
以上是关于当类没有析构函数时,智能指针或作用域指针会删除对象吗的主要内容,如果未能解决你的问题,请参考以下文章