Middle+
178
¿Cómo se puede limitar la creación de objetos de la clase en la memoria dinámica (heap) por parte de los usuarios de esa clase?
Respuesta de la IA
sobes.tech AI
Ограничить создание объектов класса в динамической памяти можно, сделав операторы new и delete приватными или защищенными.
-
Приватные операторы
newиdelete: Это самый строгий способ. Только члены класса и дружественные функции (операторnew[]также нужно объявить приватным).class NoHeapAlloc { private: void* operator new(size_t size); void operator delete(void* ptr); // Можно также запретить операторы для массивов void* operator new[](size_t size); void operator delete[](void* ptr); public: NoHeapAlloc() = default; // ... другие члены класса }; // Использование: // NoHeapAlloc* obj = new NoHeapAlloc(); // Ошибка компиляции -
Защищенные операторы
newиdelete: Позволяет создавать объекты в куче классам-наследникам, но запрещает делать это извне.class BaseNoHeapAlloc { protected: void* operator new(size_t size); void operator delete(void* ptr); void* operator new[](size_t size); void operator delete[](void* ptr); public: BaseNoHeapAlloc() = default; // ... другие члены класса }; // Наследник может создавать в куче class DerivedCanAlloc : public BaseNoHeapAlloc { public: DerivedCanAlloc() : BaseNoHeapAlloc() {} // ... }; // Использование: // BaseNoHeapAlloc* base_obj = new BaseNoHeapAlloc(); // Ошибка компиляции // DerivedCanAlloc* derived_obj = new DerivedCanAlloc(); // OK (если вызывается из члена/друга DerivedCanAlloc) // Извне все равно запрещено // BaseNoHeapAlloc* base_obj_ext = new BaseNoHeapAlloc(); // Ошибка компиляции // DerivedCanAlloc* derived_obj_ext = new DerivedCanAlloc(); // Ошибка компиляции (если не из члена класса)
В обоих случаях пользователь сможет создавать объекты только на стеке или как члены других классов:
// Правильное использование для NoHeapAlloc при приватных операторах new/delete
NoHeapAlloc obj_on_stack; // OK