Я сталкивался с этими утверждениями:
resize(n)
- Изменяет размер контейнера так, чтобы он содержал «n» элементов.
shrink_to_fit()
- Уменьшает емкость контейнера до его размера и уничтожает все элементы, превышающие емкость.
Есть ли существенная разница между этими функциями? они попадают под векторы в C ++
shrink_to_fit
меняет емкость.capacity
аsize
?Ответы:
Векторы имеют два атрибута длины, которые означают разные вещи:
size
количество используемых элементов в векторе. Это количество вещей, которые вы сохранили. Это концептуальная длина.capacity
сколько элементов поместится в объем памяти, выделенный векторомcapacity >= size
всегда должно быть правдой, но нет никаких оснований для того, чтобы они всегда были равны. Например, когда вы удаляете элемент, для сокращения выделения потребуется создать новое выделение на один контейнер меньше и переместить оставшееся содержимое поверх («распределить, переместить, освободить»).Точно так же, если
capacity == size
и вы добавите элемент, вектор может увеличить распределение на один элемент (другая операция «выделение, перемещение, освобождение»), но обычно вы собираетесь добавить более одного элемента. Если емкость должна увеличиться, вектор увеличит свою емкость более чем на один элемент, так что вы можете добавить еще несколько элементов, прежде чем переместить все снова.Обладая этими знаниями, мы можем ответить на ваш вопрос:
std::vector<T>::resize()
изменяет размер массива Если вы измените его размер меньше текущего размера, лишние объекты будут уничтожены. Если вы измените его размер больше его текущего размера, «новые» объекты, добавленные в конце, будут инициализированы по умолчанию.std::vector<T>::shrink_to_fit()
просит изменить емкость для соответствия текущему размеру. (Реализации могут или не могут удовлетворить этот запрос. Они могут уменьшить емкость, но не сделать ее равной размеру. Они могут вообще ничего не делать.) Если запрос будет выполнен, это отбросит часть или всю неиспользованную часть распределение вектора. Вы обычно используете это, когда вы закончите создание вектора и никогда не добавите к нему другой элемент. (Если вы заранее знаете, сколько предметов вы будете добавлять, было бы лучше использовать,std::vector<T>::reserve()
чтобы сообщить вектору, прежде чем добавлять какие-либо элементы, вместо того, чтобы полагаться наshrink_to_fit
что-либо.)Таким образом, вы используете,
resize()
чтобы изменить, сколько вещей концептуально в векторе.Вы используете,
shrink_to_fit()
чтобы минимизировать избыточное пространство, которое вектор выделил внутри, не меняя, сколько вещей концептуально в векторе.источник
shrink_to_fit
это не все или ничего. Реализация может уменьшить пропускную способность частично. Например, рассмотрим реализацию, которая ограничивает емкость вектора степенью двойки.Это неверное описание того, что происходит. В сущности, уничтожение всех элементов за пределами емкости не является точным.
В C ++, когда динамически используется память для объектов, есть два шага:
Когда объекты в динамически распределенной памяти удаляются, есть также два шага, которые отражают шаги построения, но в обратном порядке:
Памяти , выделенные за пределами размера контейнера просто буфер. Они не содержат должным образом инициализированных объектов. Это просто сырая память.
shrink_to_fit()
гарантирует, что дополнительной памяти нет, но в этих местах не было объектов. Следовательно, ничто не разрушается, только память освобождается.источник
Согласно стандарту C ++ относительно
shrink_to_fit
и относительно
resize
Очевидно, что функции делают разные вещи. Более того, первая функция не имеет параметров, а вторая функция имеет даже два параметра. Функция
shrink_to_fit
не меняет размер контейнера, хотя может перераспределять память.источник