Стековые8операции с векторами
Класс vectorсодержит рад методов характерных для стеков. Методpush_back() добавляет элемент в конец вектора, а методpop_back() – удаляет последний элемент вектора. Последний элемент вектора (который в данном случае соответствует элементу на вершине списка) может быть получен функциейback() рассмотренной выше.
vector <int> v;
for (int i=0; i<6; i++) v.push_back(i);
// v: 0,1,2,3,4,5
for (i=3; i<5; i++) v.pop_back();
// v: 0,1,4,5
Стековые операции можно использовать в ситуации когда вектор создается постепенно. Например, если необходимо прочитать из входного потока последовательность точек, но не известно, сколько их, не возможно сразу выделить память под вектор нужного размера:
vector<point> cities;
void add_points(point sentinel)
{
point buf;
while (cin >> buf)
{
if (buf == sentinel)
return;
cities.push_back(buf); //проверяем новую точку
}
}
Размер вектора, возвращаемый функцией size()9, неявно увеличивается функциейpush_back(), так что вектор не может переполниться (до тех пор, пока есть свободная память). Однако вектор может «переполниться» в другую сторону:
void f()
{
vector <int> v;
v.pop_back(); // состояние v становится неопределенным.
// Скорее всего произойдет исключение
// или крах программы.
v.push_back(7); //состояние v неопределенно, оно может быть плохим
}
Операции, характерные для списков
В некоторых ситуациях бывает полезно добавлять или удалять элементы из некоторой позиции в середине вектора, для этого существуют следующие методы:
template <class T, class A=allocator<T>> class vector
{
public:
//…..
// операции, характерные для списков
// добавление перед позицией определяемой итератором pos
// вставка одного элемента
iterator insert(iterator pos, const T &x);
// вставка n одинаковых элементов элемента
void insert(iterator pos, size_type n, const T &x);
//вставка элементов из последовательности заданной итераторами [first,last)
template <class In>
void insert(iterator pos, In first, In last);
//удаление элемента из позиции pos
iterator erase(iterator pos);
//удаление диапазона элементов задаваемых итераторами [first,last)
iterator erase(iterator first, iterator last);
//удаление всех элементов
void clear();
//…..
};
Итератор, возвращаемый insert(), указывает на только что вставленный элемент. Итератор, возвращаемыйerase(), указывает на элемент, следующий за последним удаленным элементом.
Следующий пример иллюстрирует использование перечисленных методов:
// заполним вектор названиями фруктов
vector<string> fruit;
fruit.push_back(“peach”);
fruit.push_back(“apple”);
fruit.push_back(“kiwi”);
// вставим в начало “orange” и запомним позицию вставленного элемента
vector<string>::iterator iter;
iter = fruit.insert(fruit.begin(),”orange”);
// вставим несколько копий “lemon” после “orange”
// обратите внимание, что необходимо сдвинуть итератор, так чтобы он указывал
// на элемент за “orange”, так как вставка осуществляется перед
// элементом указываемым итератором
iter++;
fruit.insert(fruit.begin(),”lemon”);
// вставим в конец вектора названия ягод содержащихся в другом векторе
vector<string> berries;
berries.push_back(“cherry”);
berries.push_back(“bilberry”);
berries.push_back(“strawberry”);
fruit.insert(fruit.end(),berries.begin(),berries.end());
// удалим первый элемент
fruit.erase(fruit.begin());
// удалим последний элемент
fruit.erase(fruit.end()); // ошибка! end() возвращает итератор указывающие не на
// последний элемент, а на элемент за последним
// правильный код удаления последнего элемента имеет следующий вид
fruit.erase(fruit.end()-1);