智能指针之shared_ptr

shared_ptr浅谈

简介

  • 管理一个指针的存储,提供一个有限的垃圾收集工具,可能与其他对象共享该管理。
  • shared_ptr类型的对象具有获取指针的所有权并共享所有权的能力:一旦他们拥有了所有权,当他们的最后一个成员释放所有权时,一个指针的所有者会对它的删除负责。
  • shared_ptr类型的对象具有获取指针的所有权并共享所有权的能力:一旦他们拥有了所有权,当他们的最后一个成员释放所有权时,一个指针的所有者会对它的删除负责。
  • shared_ptr对象一旦自己被销毁,就会释放他们共同拥有的对象的所有权,或者一旦它们的值通过赋值操作或对shared_ptr的显式调用进行更改,即:重置。一旦所有共享所有权的shared_ptr对象都释放了这个所有权,托管对象就会被删除(通常是通过调用::delete,但是在构造上可能会指定一个不同的删除器)。
  • 用法
header 1 header 2
default (1) constexpr shared_ptr() noexcept;
from null pointer (2) constexpr shared_ptr(nullptr_t) : shared_ptr() {}
from pointer (3) template explicit shared_ptr (U* p);
with deleter (4) template shared_ptr (U* p, D del);template shared_ptr (nullptr_t p, D del);
with allocator (5) template shared_ptr (U* p, D del, Alloc alloc);template shared_ptr (nullptr_t p, D del, Alloc alloc);
copy (6) shared_ptr (const shared_ptr& x) noexcept;template shared_ptr (const shared_ptr& x) noexcept;
copy from weak (7) template explicit shared_ptr (const weak_ptr& x);
move (8) shared_ptr (shared_ptr&& x) noexcept;template shared_ptr (shared_ptr&& x) noexcept;
move from managed (9) template shared_ptr (auto_ptr&& x);template shared_ptr (unique_ptr
// shared_ptr constructor example
#include 
#include 

struct C {int* data;};

int main () {
  std::shared_ptr<int> p1;
  std::shared_ptr<int> p2 (nullptr);
  std::shared_ptr<int> p3 (new int);
  std::shared_ptr<int> p4 (new int, std::default_delete<int>());
  std::shared_ptr<int> p5 (new int, [](int* p){delete p;}, std::allocator<int>());
  std::shared_ptr<int> p6 (p5);
  std::shared_ptr<int> p7 (std::move(p6));
  std::shared_ptr<int> p8 (std::unique_ptr<int>(new int));
  std::shared_ptr obj (new C);
  std::shared_ptr<int> p9 (obj, obj->data);

  std::cout << "use_count:\n";
  std::cout << "p1: " << p1.use_count() << '\n';
  std::cout << "p2: " << p2.use_count() << '\n';
  std::cout << "p3: " << p3.use_count() << '\n';
  std::cout << "p4: " << p4.use_count() << '\n';
  std::cout << "p5: " << p5.use_count() << '\n';
  std::cout << "p6: " << p6.use_count() << '\n';
  std::cout << "p7: " << p7.use_count() << '\n';
  std::cout << "p8: " << p8.use_count() << '\n';
  std::cout << "p9: " << p9.use_count() << '\n';
  return 0;
}
  • shared_ptr::reset
/*
void reset() noexcept;
template  void reset (U* p);
template  void reset (U* p, D del);
template  void reset (U* p, D del, Alloc alloc);
*/
// shared_ptr::reset example
#include 
#include 

int main () {
  std::shared_ptr<int> sp;  // empty

  sp.reset (new int);       // takes ownership of pointer
  *sp=10;
  std::cout << *sp << '\n';

  sp.reset (new int);       // deletes managed object, acquires new pointer
  *sp=20;
  std::cout << *sp << '\n';

  sp.reset();               // deletes managed object

  return 0;
}
Output:
10
20
  • shared_ptr::use_count
//Example1
#include  
#include  

void fun(std::shared_ptr<int> sp)
{
    std::cout << "fun: sp.use_count() == " << sp.use_count() << '\n'; 
}

int main() 
{ 
    auto sp1 = std::make_shared<int>(5);
    std::cout << "sp1.use_count() == " << sp1.use_count() << '\n'; 

    fun(sp1);
}
Output:
sp1.use_count() == 1
fun: sp.use_count() == 2

//Example2
void fun(const std::shared_ptr<int>& sp)
{
    std::cout << "fun: sp.use_count() == " << sp.use_count() << '\n'; 
}

int main() 
{ 
    auto sp1 = std::make_shared<int>(5);
    std::cout << "sp1.use_count() == " << sp1.use_count() << '\n'; 

    fun(sp1);
}
Output:
sp1.use_count() == 1
fun: sp.use_count() == 1

//Example3
void fun(const std::shared_ptr<int>& sp)
{
    std::cout << "fun: sp.use_count() == " << sp.use_count() << '\n'; 
}

int main() 
{ 
    auto sp1 = std::make_shared<int>(5);
    std::cout << "sp1.use_count() == " << sp1.use_count() << '\n'; 

    fun(sp1);
}
Output:
sp1.use_count() == 1
fun: sp.use_count() == 1
  • shared_ptr::get_deleter
#include 
#include 

struct D {    // a verbose array deleter:
  void operator()(int* p) {
    std::cout << "[deleter called]\n";
    delete[] p;
  }
};

int main () {
  std::shared_ptr<int> foo (new int[10],D());

  int * bar = new int[20];

  // use foo's deleter to delete bar (which is unmanaged):
  (*std::get_deleter(foo))(bar);

  return 0;
  // foo's deleter called automatically
}
Output:
[deleter called]
[deleter called]

你可能感兴趣的:(C++)