Для class
или struct
, таких как example
, правильный ответ - использовать new
, а не malloc()
для выделения экземпляра. Только operator new
знает, как вызывать конструкторы для struct
и его членов. Ваша проблема вызвана тем, что строковый член еще не был создан.
Однако, есть редкие случаи, когда важно, чтобы определенный участок памяти действовал так, как если бы он содержал экземпляр класса. Если у вас действительно есть такой случай, то есть вариант operator new
, который позволяет указать местоположение объекта. Это называется «новое размещение» и должно использоваться с большой осторожностью.
void *rawex = malloc(sizeof(example)); // allocate space
example ex = new(rawex) example(); // construct an example in it
ex->data = "hello world"; // use the data field, not no crash
// time passes
ex->~example(); // call the destructor
free(rawex); // free the allocation
При использовании размещения new вы обязаны указать область памяти правильного размера и выравнивания. Если вы не предоставите правильный размер или выравнивание, загадочные вещи пойдут не так. Неправильное выравнивание обычно вызывает проблемы, но также может быть и загадочным.
Кроме того, с новым размещением вы берете на себя ответственность за ручной вызов деструктора и, в зависимости от источника блока памяти, за освобождение его владельцу.
В общем, если вы уже не знаете, что вам нужно новое место размещения, оно почти наверняка вам не нужно. Он имеет законное использование, но есть неясные углы фреймворков, а не повседневные случаи.