Advertisement
mfgnik

Untitled

Mar 6th, 2023
930
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 3.45 KB | None | 0 0
  1. template<class T>
  2. class WeakPtr;
  3.  
  4. struct Block {
  5.     size_t strong_count;
  6.     size_t weak_count;
  7. };
  8.  
  9. template<class T>
  10. class SharedPtr {
  11.     explicit SharedPtr(const WeakPtr<T>& weak);
  12.  
  13.     SharedPtr() : pointer_(nullptr),  block_(new Block{1, 0}) {}
  14.  
  15.     explicit SharedPtr(T* pointer) : pointer_(pointer), block_(new Block{1, 0}) {}
  16.  
  17.     SharedPtr(const SharedPtr& other) : pointer_(other.pointer_), block_(other.block_) {
  18.         ++block_->strong_count;
  19.     }
  20.  
  21.     void Delete() {
  22.         --block_->strong_count;
  23.         if (block_->strong_count == 0) {
  24.             delete pointer_;
  25.             if (block_->weak_count == 0) {
  26.                 delete block_;
  27.             }
  28.         }
  29.     }
  30.  
  31.     SharedPtr& operator=(const SharedPtr& other) {
  32.         Delete();
  33.         pointer_ = other.pointer_;
  34.         block_ = other.block_;
  35.         ++block_->strong_count;
  36.         return *this;
  37.     }
  38.  
  39.     explicit SharedPtr(SharedPtr&& other) : pointer_(other.pointer_), block_(other.block_) {
  40.         other.pointer_ = nullptr;
  41.         other.block_ = nullptr;
  42.     }
  43.  
  44.     void Swap(SharedPtr& other) {
  45.         std::swap(pointer_, other.pointer_);
  46.         std::swap(block_, other.block_);
  47.     }
  48.  
  49.     SharedPtr& operator=(SharedPtr&& other) {
  50.         Swap(other);
  51.         return *this;
  52.     }
  53.  
  54.     ~SharedPtr() {
  55.         Delete();
  56.     }
  57.  
  58.     T operator*() const {
  59.         return *pointer_;
  60.     }
  61.  
  62.     T* Get() const {
  63.         return pointer_;
  64.     }
  65.  
  66.     Block* GetBlock() const {
  67.         return block_;
  68.     }
  69.  
  70.     void Reset() {
  71.         Delete();
  72.         pointer_ = nullptr;
  73.         block_ = new Block{1, 0};
  74.     }
  75.  
  76. private:
  77.     T* pointer_;
  78.     Block* block_;
  79. };
  80.  
  81. template <class T>
  82. class WeakPtr {
  83.     explicit WeakPtr(const SharedPtr<T>& shared) : pointer_(shared.Get()), block_(shared.GetBlock()) {
  84.         ++block_->weak_count;
  85.     }
  86.  
  87.     WeakPtr() : pointer_(nullptr), block_(new Block{0, 1}) {}
  88.  
  89.     explicit WeakPtr(const WeakPtr& other) : pointer_(other.pointer_), block_(other.block_) {
  90.         ++block_->weak_count;
  91.     }
  92.  
  93.     void Delete() {
  94.         --block_->weak_count;
  95.         if (block_->strong_count + block_->weak_count == 0) {
  96.             delete block_;
  97.         }
  98.     }
  99.  
  100.     WeakPtr& operator=(const WeakPtr& other) {
  101.         Delete();
  102.         pointer_ = other.pointer_;
  103.         block_ = other.block_;
  104.         ++block_->weak_count;
  105.         return *this;
  106.     }
  107.  
  108.     WeakPtr(WeakPtr&& other) : pointer_(other.pointer_), block_(other.block_) {
  109.         other.pointer_ = nullptr;
  110.         other.block_ = nullptr;
  111.     }
  112.  
  113.     void Swap(WeakPtr& other) {
  114.         std::swap(pointer_, other.pointer_);
  115.         std::swap(block_, other.block_);
  116.     }
  117.  
  118.     WeakPtr& operator=(WeakPtr&& other) {
  119.         Swap(other);
  120.         return *this;
  121.     }
  122.  
  123.     ~WeakPtr() {
  124.         Delete();
  125.     }
  126.  
  127.     T* Get() const {
  128.         return pointer_;
  129.     }
  130.  
  131.     Block* GetBlock() const {
  132.         return block_;
  133.     }
  134.  
  135.     bool IsExpired() const {
  136.         return block_->strong_count == 0;
  137.     }
  138.  
  139.     SharedPtr<T> Lock() const {
  140.         if (IsExpired()) {
  141.             return {};
  142.         }
  143.         return {*this};
  144.     }
  145.  
  146. private:
  147.     T* pointer_;
  148.     Block* block_;
  149. };
  150.  
  151. template <class T>
  152. SharedPtr<T>::SharedPtr(const WeakPtr<T>& other) {
  153.     if (other.IsExpired()) {
  154.         pointer_ = nullptr;
  155.     } else {
  156.         pointer_ = other.pointer_;
  157.     }
  158.     block_ = other.block_;
  159.     ++block_->strong_count;
  160. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement