ручной вызов конструктора объекта

#c #class #visual-c #gcc #constructor

#c #класс #visual-c #gcc #конструктор

Вопрос:

Не могли бы вы, пожалуйста, сказать мне, возможно ли вызвать конструктор объекта вручную? Я знаю, что это неправильно, и я бы никогда не стал делать что-то подобное в своем собственном коде, и я знаю, что могу решить эту проблему, создав и вызвав функцию инициализации, однако проблема в том, что я наткнулся на случай, когда в конструкторах объекта и его родителей тысячи строк кода…

 class MyClass()
{
    MyClass() { }
    virtual ~MyClass();

    void reset()
    {
         this->~MyClass();
         this->MyClass::MyClass(); //error: Invalid use of MyClass
    }
};
  

Комментарии:

1. Если в ЛЮБОЙ функции тысячи строк кода, значит, где-то что-то очень не так.

Ответ №1:

Вы все еще можете перенести построение / разрушение в отдельные функции и вызывать их напрямую. т.Е.

 class MyClass {
public:
    MyClass() { construct(); }
    ~MyClass() { destruct(); }

    void reset() {
        destruct();
        construct();
    }

private:
    void construct() {
        // lots of code
    }

    void destruct() {
        // lots of code
    }
};
  

Комментарии:

1. Всем большое спасибо! Я не могу поверить, что я мог пропустить это решение…

Ответ №2:

Вы могли бы использовать новый синтаксис размещения:

 this->~MyClass(); // destroy
new(this) CMyClass(); // construct at the same address
  

Ответ №3:

Конструктор вызывается с использованием размещения new

 new (address) MyClass();
  

Это создает MyClass в пустом пространстве по адресу.

Хотя я бы никогда не стал этого делать внутри класса!

Редактировать
Если у вас уже есть объект нужного типа и вы хотите присвоить ему значения по умолчанию, альтернативой является

 *this = MyClass();
  

который создает новый объект со значениями по умолчанию и присваивает это значение вашему существующему объекту.

Комментарии:

1. Проблема в том, что MyClass всегда создается в стеке

2. @Ryan: Если вы сделаете это так, как показывает @sharptooth, то утечки памяти не будет, поскольку у вас уже есть память.