Advertisement
Vserosbuybuy

C++ base guide 4

Feb 27th, 2021
708
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 8.31 KB | None | 0 0
  1. #include <iostream>
  2. #include <vector>
  3. #include <string>
  4. #include <set>
  5. #include <map>
  6. #include <algorithm>
  7.  
  8. using namespace std;
  9.  
  10. struct S {
  11.     int a;
  12. };
  13.  
  14. int main() {
  15.     // использование итераторов в векторах
  16.     vector<int> v = { 1, 2, 3, 4, 5, 3, 4 };
  17.     vector<S> v2 = { {3}, {2}, {3}, {4} };
  18.  
  19.     // можем выводить вектор с помощью итератора
  20.     for (auto it = v2.begin(); it != v2.end(); ++it) {
  21.         // две одинаковые по функционалу записи
  22.         cout << (*it).a << " ";
  23.         cout << it->a << " ";
  24.     }
  25.  
  26.     // rbegin и rend, чтобы "развернуть" итераторы
  27.     // мы получаем уже reverse итераторы
  28.     // rbegin указывает на последний элемент, и его увеличение будет
  29.     // двигать нас к началу, rend указывает "перед" первым элементом
  30.     for (auto it = v2.rbegin(); it != v2.rend(); ++it) {
  31.         // две одинаковые по функционалу записи
  32.         cout << (*it).a << " ";
  33.         cout << it->a << " ";
  34.     }
  35.  
  36.     // можем вставлять в вектор, укзаывая позицию для вставки при помощи итератора
  37.     // вставить на вторую позицию
  38.     v.insert(v.begin() + 2, 45);
  39.     // аналогично можем удалять (удаляем 3 элемент)
  40.     v.erase(v.begin() + 3);
  41.     // удаляем предпоследний
  42.     v.erase(v.end() - 2);
  43.     // стоит помнить, что обе функции работают в хужшем случае за O(n)
  44.     // (конечно, все зависит от того, куда вставляете)
  45.  
  46.     // разворачиваем вектор. Для этого передаем итератор на начало
  47.     // разворачиваемой последовательности и на конец
  48.     reverse(v.begin(), v.end());
  49.     // итераторы вектора можно двигать на число в сторону, поэтому
  50.     // можем указать не весь вектор, а его подотрезок (например, с 1 по 5 элемент)
  51.     reverse(v.begin() + 1, v.end() - 1);
  52.     // вызовет ошибку, так как пытаемся выйти за границы вектора итератором
  53.     // левее begin и правее end уходить нельзя
  54.     reverse(v.begin() - 1, v.end() - 1);
  55.  
  56.     // абсолютно аналогично можем заполнять вектор
  57.     fill(v.begin(), v.end(), 1);
  58.     fill(v.begin() + 2, v.end() - 1, 1);
  59.  
  60.     // для сортировки понадобится библиотека algorithm
  61.     // работает за O(nlog(n))
  62.     // все точно так же, указываем итераторы на начало и
  63.     // конец сортируемой последовательности
  64.     sort(v.begin() + 2, v.end());
  65.  
  66.  
  67.  
  68.     // переходим к set, для этого подключаем одноименную библиотеку
  69.     // set - множество уникальных элементов, то есть в нем не бывает дубликатов
  70.     // хранит элементы в отсортированном по возрастанию порядке
  71.     set<int> st = { 4, 2, 1 };
  72.  
  73.     // обычный for auto по-прежнему работает
  74.     // получим на выходе элементы в отсортированном порядке, то есть
  75.     // 1 2 4
  76.     for (auto x : st) {
  77.         cout << x << "\n";
  78.     }
  79.     // выводим set при помощи итераторов, вывод тот же - 1 2 4
  80.     for (auto it = st.begin(); it != st.end(); ++it) {
  81.         cout << *it << " ";
  82.     }
  83.     cout << "\n";
  84.  
  85.     // добавление элемента в set
  86.     st.insert(5);
  87.     // эти операции не изменят set, так как в нем уже есть 5
  88.     st.insert(5);
  89.     st.insert(5);
  90.     st.insert(5);
  91.     st.insert(5);
  92.  
  93.     // удаление элемента по значению
  94.     st.erase(5);
  95.     // опять никакого эффекта
  96.     st.erase(5);
  97.     st.erase(5);
  98.     // можем удалить и по итератору, для этого сначала вызовем find
  99.     // find возвращает итератор на элемент с тем же значением или st.end(), если
  100.     // в set такого элемента не оказалось
  101.     auto it = st.find(2);
  102.     // если попытаемся st.erase(st.end()) - краш
  103.     st.erase(it);
  104.  
  105.     // можем таким образом проверять, есть ли элемент
  106.     if (st.find(2) == st.end()) {
  107.         cout << "Элемента нет";
  108.     }
  109.  
  110.     // извращённый метод удаления нужного элемента
  111.     for (auto it = st.begin(); it != st.end();) {
  112.         auto it_tmp = it;
  113.         it++;
  114.         if (*it_tmp == 2) {
  115.             st.erase(it_tmp);
  116.         }
  117.     }
  118.  
  119.     // хотим удалить второй в порядке сортировки элемент, но, в отличие от вектора,
  120.     // итераторы set нельзя двигать в сторону на число, приходится костылять
  121.     auto it = st.begin();
  122.     ++it;
  123.     ++it;
  124.     st.erase(it);
  125.  
  126.     // set не хранится в памяти последовательно, поэтому использовать указатели
  127.     // для его обхода не получится, пример наглядно это демонстрирует
  128.     // первый элемент совпадет, а дальше пойдет мусор
  129.     int i = 0;
  130.     for (const int* p = &(*st.begin()); i < 3; ++i, ++p) {
  131.         cout << *it << " ";
  132.     }
  133.  
  134.  
  135.  
  136.     // переходим к map, снова библиотека с именем контейнера
  137.     // словарь. Хранит пары { ключ, значение }, в <> указываем тип
  138.     // ключа и значения соответственно
  139.     // элементы отсортированы по ключам
  140.     map<string, int> mp = { {"sad", 3}, {"one", 4}, {"dd", 211} };
  141.     // создали элемент с ключом "one"
  142.     mp["one"] = 12321;
  143.     // увеличили элемент с ключом "sad"
  144.     mp["sad"]++;
  145.     // так как элемента с таким ключом у нас нет, то map сначала создаст его
  146.     // и присвоит базовое значение (для int это 0), а потом уже применит к нему ++
  147.     // получим 1
  148.     mp["s"]++;
  149.  
  150.     // вставка пары { ключ, значение } (понятия не имею, зачем она вам может пригодиться)
  151.     // используйте квадратные скобки
  152.     mp.insert({ "sa", 22 });
  153.     // единственное преимущество - можем получить итератор на вставленный элемент
  154.     auto it = mp.insert({ "one", 23 });
  155.     // удаление по ключу
  156.     mp.erase("onesadsa");
  157.     // или итератору
  158.     mp.erase(mp.begin());
  159.  
  160.     // извращенный метод удаления по ключу через итератор
  161.     // find работает как в set
  162.     if (mp.find("one") != mp.end()) {
  163.         mp.erase(mp.find("one"));
  164.     }
  165.  
  166.     // обход map, в x оказывается очередная пара { ключ, значение }
  167.     for (auto x : mp) {
  168.         cout << "Ключ: " << x.first << ", значение: " << x.second << "\n";
  169.     }
  170.     // более элегантный метод обхода
  171.     for (auto [k, v] : mp) {
  172.         cout << "Ключ: " << k << ", значение: " << v << "\n";
  173.     }
  174.     // и, конечно, обход итераторами
  175.     for (auto it = mp.begin(); it != mp.end(); ++it) {
  176.         cout << it->first << " " << it->second << "\n";
  177.     }
  178.     return 0;
  179. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement