Запоминание константного указателя на символ?Насколько нам известно, это не вредит, если мы знаем, что мы делаем, но это хорошее поведение и почему?
Текущий код может иметь неопределенное поведение, в зависимости от версии C ++.Чтобы избежать неопределенного поведения в C ++ 14 и ниже, возьмите адрес первого элемента.Он дает неконстантный указатель:
buff.resize(size);
memcpy(&buff[0], &receiver[0], size);
Я недавно видел, как мой коллега использовал std::string
в качестве буфера ...
Это было несколько распространено в старом коде, особенно в C ++ 03.Есть несколько преимуществ и недостатков использования такой строки.В зависимости от того, что вы делаете с кодом, std::vector
может быть немного анемичным, и вы вместо этого иногда используете строку и принимаете дополнительные издержки char_traits
.
Например, std::string
обычноболее быстрый контейнер, чем std::vector
при добавлении, и вы не можете вернуть std::vector
из функции.(Или вы не могли сделать это на практике в C ++ 98, потому что C ++ 98 требовал, чтобы вектор был создан в функции и скопирован).Кроме того, std::string
позволяет выполнять поиск с более широким ассортиментом функций-членов, таких как find_first_of
и find_first_not_of
.Это было удобно при поиске по массивам байтов.
Я думаю, что вы действительно хотите / нуждаетесь в классе веревки SGI , но он никогда не попадал в STL.Похоже, что GCC libstdc ++ может предоставить его.
Существует долгая дискуссия о том, что это допустимо в C ++ 14 и ниже:
const char* dst_ptr = buff.data();
const char* src_ptr = receiver.data();
memcpy((char*) dst_ptr, src_ptr, size);
Iзнаю наверняка, это не безопасно в GCC.Однажды я сделал что-то подобное в некоторых тестах, и это привело к ошибке:
std::string buff("A");
...
char* ptr = (char*)buff.data();
size_t len = buff.size();
ptr[0] ^= 1; // tamper with byte
bool tampered = HMAC(key, ptr, len, mac);
GCC поместил один байт 'A'
в регистр AL
.Старшие 3 байта были мусором, поэтому 32-битный регистр был 0xXXXXXX41
.Когда я разыменовался в ptr[0]
, GCC разыменовал адрес мусора 0xXXXXXX41
.
Для меня были взяты две вещи: не пишите самопроверки и не пытайтесь сделать data()
неконстантный указатель.