Динамические массивы: vector

Следующим развитием динамического массивая явлется вектор.
Основные отличия:
1) Возможность изменять размер массива по ходу выполнения программы.
2) Более затратен по выделяемой памяти.

Для создания требуется подключить библиотеку:

#include <vector>

Объявление целочисленного вектора для 10 элементов:

vector<int> v(10)

или тоже самое только с начальным значениям в ячейках массива 0:

vector<int> v(10,0)

Для заполнения вектора есть 2 способа.

1) Выделяем память для n-го количества элементов и заполняем их, считывая их с клавиатуры.

int n;
cin >> n;
vector <int> a(n);
for (int i = 0; i < n; i++) 
    cin >> a[i];

2) Второй способ бывает нужен когда количество элементов неизвестно. Сначала создается пустой вектор, а потом с помощью метода push_back новый элемент добавляется в конец вектора.

int n;
cin >> n;
vector <int> a;

for (int i = 0; i < n; i++) {
      int b;
      cin >> b;
      a.push_back(b);   
}

Получить количество элементов в векторе:  

int b = a.size();

Одним из способов перебора элементов в контейнерах является iterator( итератор ), которые бывают нескольких типов, для вектора используется самый мощный из них это итератор с произвольным доступом (random-access Iterator).  Итератор с произвольным доступом помимо последовательного перемещения может обратиться к произвольному элементу вектора.

Преимущества итераторов:
1)  При удалении элементов и переборе элементов с помощью [] нам надо все время следить на количеством оставшихся элементов, чтобы не выйти за пределы вектора, а с помощью итератора можно использовать end(), указывающий на конец вектора.

2) С помощью итератора можно легко динамически удалять и вставлять элементы в векторе. 

Объявление итератора для целочисленного вектора и указание его на первый элемент в векторе:

vector<int> myvector = { 1, 2, 3, 4, 5 };       
vector<int>::iterator it = myvector.begin();     

Объявление итератора для целочисленного вектора и указание его на элемент после последнего  в векторе:

vector<int> myvector = { 1, 2, 3, 4, 5 };       
vector<int>::iterator it = myvector.end();        // указывает на элемент после последнего, подробнее.
vector<int>::iterator it1 = myvector.end() - 1 ;  // указание на последний элемент

Получение и вывод значения элемента на который указывает итератор:

cout<<*it;


Перемещение позиции итератора на 3 позиции вперед:

advance(it, 3); 

Создание нового итератора на основе существующего с продвижением на 3 позиции:

auto it1 = next(it, 3);

Вывод значений вектора с помощью итератора:

vector<int>::iterator it;
	for (it = myvector.begin(); it != myvector.end(); ++it) {
         cout<<*it<<" ";
     }

Для обхода вектора от последнего элемента к первому испольуется обратный итератор: reverse_iterator, его получение обеспечивают:
1) rbegin() -  возвращает обратный итератор, указывающий на последний элемент вектора, применение операции ++ приводит к переходу на предыдущий эдемент  
2) rend() -  возвращает обратный итератор, указывающий на предшествующий первому элемент вектора, применение операции ++ приводит к переходу  на следующий.


vector<int>::reverse_iterator it = myvector.rbegin();  //указывает на последний элемент
vector<int>::reverse_iterator it = myvector.rend();    //указывает на элемент, который стоит до первого, подробнее.