Подтвердить что ты не робот

Структура memset с std::string

У меня есть массивная структура, где все содержимое является скалярными переменными, перечислениями и массивами скаляров (на основе стека), за исключением одной переменной std::string.

Теперь, вот мой вопрос...

Могу ли я изменить структуру на 0 по всему ее размеру (например, если бы это были просто все скаляры), или это невозможно при наличии std::string? Я не уверен, что memset сделает с его внутренним представлением.

И если вы собираетесь сказать, что это хорошо/плохо, пожалуйста, объясните, почему - я хотел бы знать, почему это так:)

4b9b3361

Ответ 1

Нет, вы не можете, он перепишет внутреннее состояние строки и сделает плохие вещи. Вы могли бы обернуть все элементы POD в отдельной структуре и поместить это в свой текущий, таким образом, вы могли бы установить memset и позволить построить по умолчанию конструкцию.

Изменить:. Чтобы пояснить, строка почти наверняка будет хранить указатель на память, выделенную для хранения. Конструктор строк всегда будет запущен, прежде чем вы сможете его memset (даже если вы memset this в конструкторе вашего типа, сначала будет запускаться конструктор строк). Таким образом, вы переписываете это значение указателя и вместо указания на его хранилище указатель на NULL или какое-то другое почти определенно недопустимое значение.

Ответ 2

Здесь экзотическая идея: предположим, что ваш класс Foo имеет множество примитивных элементов, которые остаются неинициализированными в конструкторе Foo, за исключением одной строки:

class Foo
{
  int a;
  double b;
  std::string s;
};

Конструктор Foo::Foo() будет правильно инициализировать строку, но это ничего не поделает. Итак, давайте обнулить память до того, как мы построим!

void * addr = ::operator new(sizeof(Foo));
std::memset(addr, 0, sizeof(Foo));
Foo * p = new (addr) Foo;

// later

p->~Foo();
::operator delete(addr);

Конечно, было бы проще просто инициализировать все члены до нуля в конструкторе, но, возможно, у вас есть собственные причины, по которым вы не хотите создавать пользовательский конструктор.