Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
МП (Практические занятия 1, 2, 3).doc
Скачиваний:
0
Добавлен:
01.07.2025
Размер:
637.44 Кб
Скачать

Операции с итераторами вектора

Операция

Назначение

v.begin()

Возвращает итератор произвольного доступа, установленный на первый элемент

v.end()

Возвращает итератор произвольного доступа, установленный на позицию, следующую за последним элементом

v.cbegin()

Возвращает константный итератор произвольного доступа, устано-вленный на первый элемент (стандарт С++11)

v.cend()

Возвращает константный итератор произвольного доступа, устано-вленный на позицию, следующую за последним элементом (стандарт С++11)

v.rbegin()

Возвращает обратный итератор, установленный на первый элемент при обратном обходе

v.rend()

Возвращает обратный итератор на позицию, следующую за последним элементом при обратном обходе

v.crbegin()

Возвращает константный обратный итератор, установленный на первый элемент при обратном обходе (стандарт С++ 11)

v.crend()

Возвращает константный обратный итератор, установленный на первый элемент при обратном обходе (стандарт С++11)

Разработчиками STL приняты соглашения, согласно которым при указании диапазона начальный итератор показывает на первый элемент диапазона, а конечный – на элемент, следующий за последним элементом диапазона (запредельное значение). В связи с этим оригинально решена проблема продвижения по контейнеру в обратном направлении: реверсивный итератор начала диапазона указывает на последний элемент вектора, а реверсивный итератор конца диапазона – на фиктивный элемент, стоящий перед начальным элементом вектора.

Таблица 25.7

Втавка и удаление элементов

Операция

Назначение

v.insert(pos,elem)

Вставляет в позицию pos элемент elem, возвращает позицию следующего элемента

v.insert(pos,n,elem)

Вставляет n элементов elem в позицию pos

v.insert(pos,beg,end)

Вставляет элементы интервала [beg, end) в позицию pos

v.insert(pos,initlist)

Вставляет копии всех элементов списка инициа-лизации initlist перед позицией итератора pos и возвращает позицию первого нового элемента (или итератор pos, если новых элементов нет) (стандарт С++ 11)

v.emplace(pos,args)

Вставляет новый элемент, инициализированный спис-ком аргументов args перед позицией итератора pos, и возвращает позицию нового элемента (стандарт С++ 11)

v.emplace_back(pos,args)

Добавляет в конец вектора новый элемент, инициа-лизированный списком аргументов args (не возвращает ничего) (стандарт С++ 11)

v.push_back(elem)

Вставляет элемент elem в конец вектора

v.pop_back()

Удаляет последний элемент

v.erase(pos)

Удаляет элемент в позиции pos и возвращает позицию следующего элемента

v.erase(beg,end)

Удаляет все элементы из интервала [beg, end)

v. resize(num)

Приводит контейнер к размеру num

v. resize(num, elem)

Приводит контейнер к размеру num, новые элементы создаются как копии elem

v. clear ()

Удаляет содержимое вектора

Рассмотрим пример программы, демонстрирующей методы класса vector<>.

//Листинг 25.3

#include<iostream>

#include<vector>

using namespace std;

int main()

{

setlocale(LC_CTYPE,"Russian");

int m[] = {1,5,3,4,0,2,1,4,8,3};

vector <int> v1; //конструктор по умолчанию

//вектор из 20 пустых значений

vector <int> v2(20);

vector <int> v3(10,1);//вектор из 10 единиц

vector <int> v4(v3); //копия вектора v3

//вектор из 10 элементов массива m

vector <int> v5(m, m+10);

cout<<"size v5 = "<<v5.size()<<endl;

cout<<"empty v5 = "<<v5.empty()<<endl;

cout<<"max_size v5 = "

<<v5.max_size()<<endl;

cout<<"capacity v5 = "

<<v5.capacity()<<endl;

v5.reserve(20);

cout<<"capacity v5 = "

<<v5.capacity()<<endl;

//операции сравнения

if (v3 == v4) cout<<"v3 is equal v4\n";

// Вектор из 3-х элементов массива m

vector<int> v6(m, m+3);

if (v6<v5) cout<<"v6 < v5\n";

//операции присваивания

v1= v6;

//вывод вектора на экран

//с помощью операции индексирования

for (int i = 0; i<v1.size(); i++)

cout<<v1[i]<<" ";

cout<<endl;

v2.assign(100,0);

cout<<"size v2 = "<<v2.size()<<endl;

cout<<"capacity v2 = "<<v2.capacity()

<<endl;

v6.swap(v5);

cout<<"size v6 = "<<v6.size()<<endl;

cout<<"size v5 = "<<v5.size()<<endl;

//вывод вектора на экран с помощью итератора

vector<int>:: iterator it;

for(it=v5.begin();it<v5.end();it++)

cout<<*it<<'\t' ;

cout<<endl;

vector <int> v;

// Заполнение вектора

for(int i = 0; i < 10; i++) v.push_back(i);

while(!v.empty()) // Пока вектор не пустой

{ // Вывод на консоль последнего элемента

cout<<v.back()<<' ';

//Удаление последнего элемента

v.pop_back();

}

cout<<endl;

vector <int> q(5,2);// Вектор из пяти двоек

// Вставить первые 5 нулей

q.insert(q.begin(),5,0);

// Вставить следующие 5 единиц

q.insert(q.begin()+5,5,1);

for(int i=0;i<15;i++)

cout<<q[i]<<' ';

cout<<endl;

// Удалить 5 единиц

q.erase(q.begin()+5,q.begin()+10);

for(int i=0;i<10;i++)

cout<<q[i]<<' ';

cout<<endl;

q.resize(5);// Изменить размер вектора до 5

cout<<"size q = "<<q.size()<<endl;

q.clear(); // Очистить содержимое

cout<<"empty q = "<<q.empty()<<endl;

return 0;

}

Результаты выполнения программы:

size v5 = 10

empty v5 = 0

max_size v5 = 1073741823

capacity v5 = 10

capacity v5 = 20

v3 is equal v4

v6 < v5

1 5 3

size v2 = 100

capacity v2 = 100

size v6 = 10

size v5 = 3

1 5 3

9 8 7 6 5 4 3 2 1 0

0 0 0 0 0 1 1 1 1 1 2 2 2 2 2

0 0 0 0 0 2 2 2 2 2

size q = 5

empty q = 1

В операторе присваивания v1=v6, несмотря на то, что переменной v1 изначально не было выделено памяти для хранения данных, контейнер сам выделил необходимую память, куда и скопировал содержимое переменной v6, метод assign() также выделил необходимую память для вектора v2, метод swap () обменял не только данные двух векторов, но и их размеры.

Конструкция vector<int>:: iterator it обеспечивает описание итератора it для вектора с данными типа int, и в ней потребовалось явно указать имя контейнера с уточнением типа данных. Доступ же к данным возможен применением обычной операции разадресации итератора it. Далее, установив итератор на начало вектора, it= v5.begin(), передвигаемся по вектору, наращивая итератор it++, до достижения конца вектора it < v5.end(). *it — это значение элемента вектора (операция разадресации для итератора перегружена и имеет тот же смысл, что и для указателя).

При работе с контейнерами STL нужно иметь в виду, что при совершении операций вставки элемента или увеличения размера контейнера может автоматически происходить перераспределение памяти, т. е. для данных выделяется новая область памяти, куда они и копируются, а "старая" область памяти освобождается. Это приводит к тому, что после таких операций необходимо заново определять итераторы начала и конца контейнера.