C++11標準ライブラリのstd::shared_ptr
では、ヌルポインタを所有することが可能となっている。
デフォルトコンストラクトされたshared_ptr
オブジェクトは空(empty)となる。一方、明示的にnullptr
を与えてコンストラクトしたshared_ptr
オブジェクトは “ヌルポインタを所有(own)する” *1。この場合はshared_ptr
オブジェクト破棄時にカスタムデリータが呼ばれる。
#include <memory> #include <iostream> int main() { auto custom_deleter = [](void* p){ assert(p == nullptr); std::cout << "deleter called" << std::endl; }; std::shared_ptr<void> sp(nullptr, custom_deleter); } // 標準出力に"deleter called"が出力される
N3337 20.7.2.2/p1, 20.7.2.2.1/p1-2,9-10, 20.7.2.2.2/p1より部分引用。
(snip) A
shared_ptr
object is empty if it does not own a pointer.
constexpr shared_ptr() noexcept;1 Effects: Constructs an empty
shared_ptr
object.
2 Postconditions:use_count() == 0 && get() == 0
.template <class Y, class D> shared_ptr(Y* p, D d); template <class D> shared_ptr(nullptr_t p, D d);9 Effects: Constructs a
shared_ptr
object that owns the objectp
and the deleterd
. (snip)
10 Postconditions:use_count() == 1 && get() == p
.
~shared_ptr();
1 Effects:
- If
*this
is empty or shares ownership with anothershared_ptr
instance (use_count() > 1
), there are no side effects.- Otherwise, if
*this
owns an objectp
and a deleterd
,d(p)
is called.- Otherwise,
*this
owns a pointerp
, anddelete p
is called.
追記:"empty" の定義が曖昧?
[twitter:@k_satoda]さんからの指摘を受けて。
N3337 20.7.2.2/p1は "A shared_ptr
object is empty if it does not own an object a pointer." とすべきかも。
関連URL
*1:ヌルポインタ定数として NULL や 0 を指定した場合も同様の動作となる。