shared_ptr到数组:应该使用它吗? [英] shared_ptr to an array : should it be used?
问题描述
只是关于 shared_ptr
的小型查询。
Just a small query regarding shared_ptr
.
使用 shared_ptr
指向数组是个好习惯吗?
例如 shared_ptr< int> sp(new int [10]);
Is it a good practice to use shared_ptr
pointing to an array?
e.g shared_ptr<int> sp(new int[10]);
如果没有,那么任何人都可以告诉我为什么?我已经知道的一个原因是不能增加/减少 shared_ptr
。
If not then can anyone please tell me why? One reason i am already aware of is one can not increment/decrement the shared_ptr
. Hence it can not be used like a normal pointer to an array.
推荐答案
默认情况下, shared_ptr
将在没有更多引用保留到托管对象上时调用 delete
。但是,当使用 new []
分配时,需要调用 delete []
,而不是 delete
,释放资源。
By default, shared_ptr
will call delete
on the managed object when no more references remain to it. However, when you allocate using new[]
you need to call delete[]
, and not delete
, to free the resource.
为了使用数组正确使用 shared_ptr
,必须提供自定义删除程序。
In order to correctly use shared_ptr
with an array, you must supply a custom deleter.
template< typename T >
struct array_deleter
{
void operator ()( T const * p)
{
delete[] p;
}
};
创建shared_ptr如下:
Create the shared_ptr as follows:
std::shared_ptr<int> sp( new int[10], array_deleter<int>() );
现在 shared_ptr
将正确调用 delete []
销毁受管对象。
Now shared_ptr
will correctly call delete[]
when destroying the managed object.
,使用C ++ 11,您可以使用 std :: default_delete
部分专业化数组类型,而不是上面的 array_deleter
。
As shown in the comments, with C++11, you can use the std::default_delete
partial specialization for array types instead of array_deleter
above.
std::shared_ptr<int> sp( new int[10], std::default_delete<int[]>() );
您也可以使用lambda表达式。
You can also use a lambda expression instead of functors.
std::shared_ptr<int> sp( new int[10], []( int *p ) { delete[] p; } );
此外,除非您确实需要共享对象, unique_ptr
更适合此任务,因为它对数组类型有部分专门化。
Also, unless you actually need to share the managed object, a unique_ptr
is better suited for this task, since it has a partial specialization for array types.
std::unique_ptr<int[]> up( new int[10] ); // this will correctly call delete[]
由C + +扩展库引入的更改基础库
shared_ptr
通过图书馆基础技术规范(TS)增加,以允许它在拥有对象数组的情况下工作;将不需要明确提供删除器。此TS的 shared_ptr
更改的当前草案可以在 N4082 。这些更改将通过 std :: experimental
命名空间访问,并包含在< experimental / memory>
。支持数组的 shared_ptr
的一些相关更改是:
Changes introduced by the C++ Extensions for Library Fundamentals
shared_ptr
is being augmented by the Library Fundamentals Technical Specification (TS) to allow it to work out of the box for the cases when it owns an array of objects; there'll be no need to explicitly supply a deleter. The current draft of the shared_ptr
changes slated for this TS can be found in N4082. These changes will be accessible via the std::experimental
namespace, and included in the <experimental/memory>
header. A few of the relevant changes to support shared_ptr
for arrays are:
—成员类型的定义 element_type
更改
— The definition of the member type element_type
changes
typedef T element_type;
typedef T element_type;
typedef typename remove_extent<T>::type element_type;
—正在添加会员运算符[]
— Member operator[]
is being added
element_type& operator[](ptrdiff_t i) const noexcept;
—与 unique_ptr
数组的部分专门化不同, shared_ptr< T []>
和 shared_ptr< ; T [N]>
将有效,并且将导致在被管理的对象数组上调用 delete []
。 >
— Unlike the unique_ptr
partial specialization for arrays, both shared_ptr<T[]>
and shared_ptr<T[N]>
will be valid and both will result in delete[]
being called on the managed array of objects.
template<class Y> explicit shared_ptr(Y* p);
需要: Y
应为完整类型。当 T
是数组类型或 delete p
delete [] p
/ code>,当 T
不是一个数组类型,应该是良好的形式,应该有良好的定义行为,不会抛出异常。当 T
为 U [N]
, Y(*)[N] 可转换为
T *
;当 T
是 U []
, Y(*)[]
应可转换为 T *
;否则 Y *
可转换为 T *
。
Requires: Y
shall be a complete type. The expression delete[] p
, when T
is an array type, or delete p
, when T
is not an array type, shall be well-formed, shall have well defined behavior, and shall not throw exceptions. When T
is U[N]
, Y(*)[N]
shall be convertible to T*
; when T
is U[]
, Y(*)[]
shall be convertible to T*
; otherwise, Y*
shall be convertible to T*
.
这篇关于shared_ptr到数组:应该使用它吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!