shushus

Спринт 7. Присваивание объектов. Задание 2.

Jan 12th, 2023
311
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 4.34 KB | None | 0 0
  1. #include <algorithm>
  2. #include <cassert>
  3. #include <stdexcept>
  4. #include <vector>
  5. #include <new>
  6. //#include "scopedptr.h"
  7.  
  8. using namespace std;
  9.  
  10. template <typename T>
  11. class PtrVector {
  12. public:
  13.     PtrVector() = default;
  14.  
  15.     PtrVector(const PtrVector& other) {
  16.         items_.reserve(other.items_.size());
  17.         try {
  18.             for (auto p : other.items_) {
  19.                 auto p_copy = p ? new T(*p) : nullptr;
  20.  
  21.                 items_.push_back(p_copy);
  22.             }
  23.         } catch (...) {
  24.             DeleteItems();
  25.             throw;
  26.         }
  27.     }
  28.    
  29.     PtrVector& operator=(const PtrVector& rhs) {
  30.         if (this != &rhs) {
  31.             auto rhs_copy(rhs);
  32.             items_.swap(rhs_copy.items_);
  33.         }
  34.         return *this;
  35.     }
  36.  
  37.     void swap(PtrVector& other) noexcept;
  38.  
  39.     ~PtrVector() {
  40.         DeleteItems();
  41.     }
  42.  
  43.     vector<T*>& GetItems() noexcept {
  44.         return items_;
  45.     }
  46.  
  47.     vector<T*> const& GetItems() const noexcept {
  48.         return items_;
  49.     }
  50.  
  51. private:
  52.     void DeleteItems() noexcept {
  53.         for (auto p : items_) {
  54.             delete p;
  55.         }
  56.     }
  57.  
  58.     vector<T*> items_;
  59. };
  60.  
  61. class Tentacle {
  62. public:
  63.     explicit Tentacle(int id) noexcept : id_(id) {}
  64.  
  65.     int GetId() const noexcept {
  66.         return id_;
  67.     }
  68.  
  69.     Tentacle* GetLinkedTentacle() const noexcept {
  70.         return linked_tentacle_;
  71.     }
  72.     void LinkTo(Tentacle& tentacle) noexcept {
  73.         linked_tentacle_ = &tentacle;
  74.     }
  75.     void Unlink() noexcept {
  76.         linked_tentacle_ = nullptr;
  77.     }
  78.  
  79. private:
  80.     int id_ = 0;
  81.     Tentacle* linked_tentacle_ = nullptr;
  82. };
  83.  
  84. class Octopus {
  85. public:
  86.     Octopus()
  87.         : Octopus(8) {
  88.     }
  89.  
  90.     explicit Octopus(int num_tentacles) {
  91.         Tentacle* ttentacle = nullptr;
  92.         try {
  93.             for (int i = 1; i <= num_tentacles; ++i) {
  94.                 ttentacle = new Tentacle(i);
  95.                 tentacles_.GetItems().push_back(ttentacle);
  96.                
  97.                 ttentacle = nullptr;
  98.             }
  99.         } catch (const std::bad_alloc&) {
  100.             Cleanup();
  101.             delete ttentacle;
  102.             throw;
  103.         }
  104.     }
  105.  
  106.     ~Octopus() {
  107.         Cleanup();
  108.     }
  109.  
  110.     Tentacle& AddTentacle() {
  111.         Tentacle* ttentacle = new Tentacle(tentacles_.GetItems().size() + 1);
  112.         tentacles_.GetItems().push_back(ttentacle);
  113.         return *ttentacle;
  114.     }
  115.  
  116.     int GetTentacleCount() const noexcept {
  117.         return static_cast<int>(tentacles_.GetItems().size());
  118.     }
  119.  
  120.     const Tentacle& GetTentacle(size_t index) const {
  121.         return *tentacles_.GetItems().at(index);
  122.     }
  123.     Tentacle& GetTentacle(size_t index) {
  124.         return *tentacles_.GetItems().at(index);
  125.     }
  126.  
  127. private:
  128.     void Cleanup() {
  129.         for (Tentacle* ttentacle : tentacles_.GetItems()) {
  130.             delete ttentacle;
  131.         }
  132.         tentacles_.GetItems().clear();
  133.     }
  134.  
  135.     PtrVector<Tentacle> tentacles_;
  136. };
  137.  
  138. int main() {
  139.     {
  140.         Octopus octopus1(3);
  141.  
  142.         octopus1.GetTentacle(2).LinkTo(octopus1.GetTentacle(1));
  143.  
  144.         Octopus octopus2(10);
  145.  
  146.         octopus2 = octopus1;
  147.  
  148.         assert(octopus2.GetTentacleCount() == octopus1.GetTentacleCount());
  149.         for (int i = 0; i < octopus2.GetTentacleCount(); ++i) {
  150.             auto& tentacle1 = octopus1.GetTentacle(i);
  151.             auto& tentacle2 = octopus2.GetTentacle(i);
  152.             assert(&tentacle2 != &tentacle1);
  153.             assert(tentacle2.GetId() == tentacle1.GetId());
  154.             assert(tentacle2.GetLinkedTentacle() == tentacle1.GetLinkedTentacle());
  155.         }
  156.     }
  157.  
  158.     {
  159.         Octopus octopus(3);
  160.  
  161.         octopus.GetTentacle(0).LinkTo(octopus.GetTentacle(1));
  162.  
  163.         vector<pair<Tentacle*, Tentacle*>> tentacles;
  164.         for (int i = 0; i < octopus.GetTentacleCount(); ++i) {
  165.             tentacles.push_back({&octopus.GetTentacle(i), octopus.GetTentacle(i).GetLinkedTentacle()});
  166.         }
  167.  
  168.         octopus = octopus;
  169.  
  170.         assert(octopus.GetTentacleCount() == static_cast<int>(tentacles.size()));
  171.         for (int i = 0; i < octopus.GetTentacleCount(); ++i) {
  172.             auto& tentacle_with_link = tentacles.at(i);
  173.             assert(&octopus.GetTentacle(i) == tentacle_with_link.first);
  174.             assert(octopus.GetTentacle(i).GetLinkedTentacle() == tentacle_with_link.second);
  175.         }
  176.     }
  177. }
Advertisement
Add Comment
Please, Sign In to add comment