您的位置:首页 > 其它

一个简单smart pointer的实现

2012-07-29 01:09 253 查看
转自出处

  学习这个代码有助于理解shared_ptr指针的实现方法
  smart.cpp
  1 namespace smart
  2 {
  3 // 引用计数类.
  4 class smart_count
  5 {
  6 public:
  7 smart_count(int c = 0) : use_count(c) {}
  8 ~smart_count() {}
  9
  10 // 增加引用计数, 并返回计数值.
  11 int addref() { return ++use_count; }
  12 // 减少引用计数, 并返回计数值.
  13 int release() { return --use_count; }
  14
  15 private:
  16 // 计数变量.
  17 int use_count;
  18 };
  19
  20 // 智能指针.
  21 template <class T>
  22 class smart_ptr
  23 {
  24 public:
  25 // 构造指针, 并使引用计数置为1.
  26 explicit smart_ptr (T* ptr) : p(ptr), u(new smart_count(1))
  27 {}
  28
  29 // 构造空指针.
  30 explicit smart_ptr () : p(NULL), u(NULL)
  31 {}
  32
  33 // 智能指针析构.
  34 ~smart_ptr (void)
  35 {
  36 // 如果引用计数等于0, 则删除数据和引用计数, 并置p为NULL.
  37 // 此处需要注意的是, 共用的u并未置为 NULL, 在其它指针析构
  38 // 时, p为NULL, 则不会重复delete.
  39 if (p && u->release() <= 0)
  40 {
  41 delete p;
  42 delete u;
  43 p = NULL;
  44 }
  45 }
  46
  47 // 智能指针拷贝构造函数.
  48 smart_ptr (const smart_ptr<T>& t)
  49 {
  50 p = t.p;
  51 u = t.u;
  52
  53 if (u) // 必须判断空值.
  54 {
  55 u->addref(); // 增加引用计数.
  56 }
  57 }
  58
  59 // 指针赋值.
  60 void operator= (smart_ptr<T>& t)
  61 {
  62 // 首先将引用计数减1, 然后再判断是否小于0, 如果小于0, 则delete.
  63 if (p && u->release() <= 0)
  64 {
  65 delete p;
  66 delete u;
  67 }
  68
  69 // 直接赋值.
  70 p = t.p;
  71 u = t.u;
  72
  73 if (u) // 必须判断空值.
  74 {
  75 u->addref(); // 增加引用计数.
  76 }
  77 }
  78

  79 // 重载->操作和*操作符.
  80 T *operator-> (void) { return p; }
  81 T& operator *(void) { return *p; }
  82 // 重载!操作符.
  83 bool operator! () const { return !p;}
  84
  85 // 重载指针bool值操作符.
  86 typedef smart_ptr<T> this_type;
  87 typedef T * this_type::*unspecified_bool_type;
  88 operator unspecified_bool_type() const { return !p ? 0: &this_type::p; }
  89 // 得到原指针.
  90 T* get() { return p; }
  91 void reset(T* ptr)
  92 {
  93 // 首先将引用计数减1, 然后再判断是否小于0, 如果小于0, 则delete.
  94 if (p && u->release() <= 0)
  95 {
  96 delete p;
  97 delete u;
  98 }
  99
  100 // 赋值, 如果是NULL, 则不创建引用计数.
  101 p = ptr;
  102 if (p)
  103 u = new smart_count(1);
  104 else
  105 u = NULL;
  106 }
  107
  108 void reset(smart_ptr<T>& t)
  109 {
  110 // 首先将引用计数减1, 然后再判断是否小于0, 如果小于0, 则delete.
  111 if (p && u->release() <= 0)
  112 {
  113 delete p;
  114 delete u;
  115 }
  116
  117 // 赋值.
  118 p = t.p;
  119 u = t.u;
  120
  121 if (u) // 必须判断空值.
  122 {
  123 u->addref(); // 增加引用计数.
  124 }
  125 }
  126
  127 private:
  128 T* p;
  129 smart_count* u;
  130 };
  131
  132 // 重载==操作符.
  133 template<class T, class U> inline bool operator==(smart_ptr<T> & a, smart_ptr<U> & b)
  134 {
  135 return a.get() == b.get();
  136 }
  137
  138 // 重载!=操作符.
  139 template<class T, class U> inline bool operator!=(smart_ptr<T> & a, smart_ptr<U> & b)
  140 {
  141 return a.get() != b.get();
  142 }
  143 }
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: