Специализация std::vector<bool>
как указано в C ++ 11 23.3.7 / 1, не объявляет член данных (например, упомянутый Вот а также Вот).
Вопрос в том, почему std :: vector не имеет .data ()? Это тот же вопрос, что и почему вектор bools не хранится в памяти непрерывно. Каковы преимущества не делать этого?
Почему указатель на массив bools не может быть возвращен?
Почему std :: vector не имеет .data ()?
Потому что std::vector<bool>
хранит несколько значений в 1 байт.
Думайте об этом как о сжатой системе хранения, где каждому логическому значению требуется 1 бит. Таким образом, вместо одного элемента на блок памяти (один элемент на ячейку массива) макет памяти может выглядеть следующим образом:
Предполагая, что вы хотите проиндексировать блок, чтобы получить значение, как бы вы использовали оператор []
? Не может вернуться bool&
(так как он вернет один байт, который хранит более одного bools
), таким образом, вы не могли назначить bool*
к этому. Другими словами bool *bool_ptr =&v[0];
является не допустимый код, и приведет к ошибке компиляции.
Более того, правильная реализация может не иметь такой специализации и не выполнять оптимизацию памяти (сжатие). Так data()
придется копировать в ожидаемый тип возвращаемого значения в зависимости от реализации (или стандарт должен форсировать оптимизацию, а не просто позволять это).
Почему указатель на массив bools не может быть возвращен?
Так как std::vector<bool>
является не хранится в виде массива bools, поэтому прямой указатель не может быть возвращен. Это можно сделать, скопировав данные в массив и вернув этот массив, но не стоит этого делать (если они это сделают, я думаю, что это работает как data()
для всех контейнеров, которые будут вводить в заблуждение).
Каковы преимущества не делать этого?
Оптимизация памяти.
Обычно использование памяти в 8 раз меньше, так как в одном байте хранится несколько битов. Если быть точным, CHAR_BIT
раз меньше.
Других решений пока нет …