Middle+
Jak ograniczyć liczbę instancji klasy w C++?
sobes.tech AI
Odpowiedź od AI
Istnieje kilka metod, główne to:
-
Użycie statycznej zmiennej licznika:
- Utwórz statyczną zmienną typu
intdo śledzenia liczby utworzonych instancji. - Zwiększ licznik w konstruktorze.
- Zmniejsz licznik w destruktorze.
- W konstruktorze sprawdź wartość licznika i, jeśli przekracza limit, wyrzuć wyjątek lub podejmij inne działania.
- Uczyń konstruktor prywatnym lub chronionym, a tworzenie instancji realizuj przez statyczną funkcję fabryczną, która wykonuje sprawdzenie.
- Zabroń kopiowania i przenoszenia.
#include <iostream> #include <stdexcept> class LimitedInstances { private: static int instance_count; static const int max_instances = 3; LimitedInstances() { if (instance_count >= max_instances) { throw std::runtime_error("Osiągnięto maksymalną liczbę instancji."); } instance_count++; std::cout << "Utworzono instancję. Razem: " << instance_count << std::endl; } // Zabroń kopiowania i przenoszenia LimitedInstances(const LimitedInstances&) = delete; LimitedInstances& operator=(const LimitedInstances&) = delete; LimitedInstances(LimitedInstances&&) = delete; LimitedInstances& operator=(LimitedInstances&&) = delete; public: ~LimitedInstances() { instance_count--; std::cout << "Zniszczono instancję. Razem: " << instance_count << std::endl; } static LimitedInstances* create_instance() { return new LimitedInstances(); } }; int LimitedInstances::instance_count = 0; - Utwórz statyczną zmienną typu
-
Użycie wzorca Singleton z modyfikacją:
- Zazwyczaj Singleton gwarantuje jedną instancję. Aby ograniczyć liczbę instancji, można go zmodyfikować, zarządzając dostępem do tworzenia przez funkcję statyczną i śledząc utworzone obiekty w prywatnym statycznym kontenerze (np.
std::vectorlubstd::list).
#include <iostream> #include <vector> #include <stdexcept> class NLimitedInstances { private: static std::vector<NLimitedInstances*> instances; static const int max_instances = 2; NLimitedInstances() { std::cout << "NLimitedInstances utworzony." << std::endl; } // Zabroń kopiowania i przenoszenia NLimitedInstances(const NLimitedInstances&) = delete; NLimitedInstances& operator=(const NLimitedInstances&) = delete; NLimitedInstances(NLimitedInstances&&) = delete; NLimitedInstances& operator=(NLimitedInstances&&) = delete; public: static NLimitedInstances* get_instance() { if (instances.size() >= max_instances) { throw std::runtime_error("Osiągnięto maksymalną liczbę NLimitedInstances."); } NLimitedInstances* new_instance = new NLimitedInstances(); instances.push_back(new_instance); return new_instance; } static void destroy_instance(NLimitedInstances* instance) { // Szukaj i usuwaj instancję z wektora for (auto it = instances.begin(); it != instances.end(); ++it) { if (*it == instance) { delete *it; instances.erase(it); std::cout << "NLimitedInstances zniszczony." << std::endl; return; } } } ~NLimitedInstances() = default; // lub dodaj logikę czyszczenia }; std::vector<NLimitedInstances*> NLimitedInstances::instances; - Zazwyczaj Singleton gwarantuje jedną instancję. Aby ograniczyć liczbę instancji, można go zmodyfikować, zarządzając dostępem do tworzenia przez funkcję statyczną i śledząc utworzone obiekty w prywatnym statycznym kontenerze (np.
Oba podejścia wymagają ostrożnego zarządzania zasobami, szczególnie przy użyciu new. Wzorzec Singleton z modyfikacją może być bardziej skomplikowany w implementacji destrukcji obiektów, szczególnie jeśli ich cykl życia nie pokrywa się z końcem programu.
Wybór metody zależy od konkretnych wymagań i złożoności systemu. Podejście z licznikiem statycznym jest ogólnie prostsze do zrozumienia i wdrożenia.