Назад к вопросам
Middle
112
questionbank

В чем разница между созданием объекта shared_ptr через конструктор и использованием функции make_shared?

Sobes Copilot

Получайте ответы в реальном времени

Ответ от нейросети

sobes.tech AI

Разница между созданием объекта через конструктор shared_ptr и функцией make_shared заключается в механизме выделения памяти и эффективности.

  • Конструктор shared_ptr: Выделяет память для объекта и управляющего блока (счетчики ссылок) отдельно.
    #include <memory>
    
    class MyClass {
    public:
        int value;
        MyClass(int v) : value(v) {}
    };
    
    int main() {
        // Выделение памяти для MyClass и управляющего блока происходит отдельно
        std::shared_ptr<MyClass> ptr1(new MyClass(10));
        return 0;
    }
    
  • make_shared: Выделяет память для объекта и управляющего блока одним блоком памяти.
    #include <memory>
    
    class MyClass {
    public:
        int value;
        MyClass(int v) : value(v) {}
    };
    
    int main() {
        // Выделение памяти для MyClass и управляющего блока происходит одним блоком
        std::shared_ptr<MyClass> ptr2 = std::make_shared<MyClass>(20);
        return 0;
    }
    
Особенность Конструктор shared_ptr make_shared
Выделение памяти Объект и управляющий блок отдельно Объект и управляющий блок одним блоком
Количество операций выделения памяти Две Одна
Эффективность Менее эффективен Более эффективен (меньше накладных расходов)
Безопасность исключений Требует осторожности в выражении new T(...) Исключительно безопасен
Возможность использования с массивами Да (с пользовательским deleter) Нет (до C++20), да (с C++20 для shared_ptr<T[]>)

Использование make_shared предпочтительнее, если нет специфических причин использовать конструктор, так как это более эффективно и безопасно с точки зрения исключений. Конструктор может потребоваться, например, при создании shared_ptr из уже существующего "сырого" указателя.