Выведите свои навыки C ++ на новый уровень, используя «современный» C ++
Вы знаете синтаксис и кодирование на языке C ++. Но знаете ли вы, что делает вас современным программистом на C ++? Использует ли ваш код функции, представленные в C ++ 11, 14 или 17? Используете ли вы в своем приложении классы стандартной библиотеки? Знаете ли вы о лямбда-функциях C ++, интеллектуальных указателях и выразительных циклах for?
Если ваш ответ отрицательный, вот несколько советов, которые помогут вам улучшить свои навыки программирования на C ++ и сделать вас современным программистом на C ++.
1. Стандартные библиотечные контейнеры
Vector, Array и List - это базовые библиотечные контейнеры, используемые в C ++.
Vector выделяет память в куче, поэтому элементы можно динамически добавлять и удалять. Это полезно, когда размер контейнера неизвестен и может измениться во время выполнения.
Если размер контейнера фиксированный напр. Месяцев в году (12), используйте вместо этого std: array. В отличие от Vector, Array выделяет память в стеке и обеспечивает более быстрый доступ к элементам.
Список полезен для последовательного доступа к элементам, например, для хранения списка заказов, отсортированных по дате. В худшем случае для доступа к элементу требуется пройти через конец списка.
В дополнение к этому, C ++ также предоставляет другие стандартные библиотечные контейнеры, такие как stack, queue, dequeue, priority_queue, карта, unordered_map.
Стек полезен для операций push, pop, top над элементами в контейнере.
Очередь полезен для отправки, выталкивания и выполнения других операций с элементами только в начале очереди.
Dequeue аналогично очереди, но выполняет операции с элементами в начале и в конце очереди.
Priority Queue аналогично очереди, но вставляет элемент в контейнер на основе приоритета, связанного с ними, например. вставлять студентов в зависимости от ранга
Карта используется для хранения пар ключей и значений, отсортированных по значениям ключей.
Неупорядоченная карта - это пары ключей и значений без сортировки.
Если вы новичок в C ++, начните с использования vector. Если вы чувствуете, что вам нужен стек или карта, продолжайте и начните использовать эти контейнеры. Также напишите свой код таким образом, чтобы упростить переключение между контейнерами, например, используя ключевое слово auto. В будущем, если вы захотите переключиться с dequeue на queue, это будет намного проще.
2. Лямбды
В более старых версиях C ++ указатели на функции использовались для хранения поведения функции внутри переменной. Позже к функции можно было получить доступ с помощью указателя. Недостатки указателей на функции в том, что их было сложно понять и плохо читалось. Поэтому они придумали лямбды, которые заменяют традиционные указатели на функции. Все современные языки программирования, такие как Java, Kotlin, используют Lambdas.
Пример лямбда-выражения в C ++ приведен ниже.
[](){} // Empty Lambda function
Где [] представляет предложение захвата для захвата значений, () представляет параметры, переданные функции, а {} содержит тело лямбда-функции.
//Example Lambda function isOdd auto isOdd = [](int candidate){ return candidate % 2 != 0 }; bool is3Odd = isOdd(3); //Returns true as 3 is Odd bool is4Odd = isOdd(4); //Returns false as 4 is Even vector nums{2, 3, 4, -1, 1}; //Find the number of Odd Items in the Vector. Returns 3 int odds = std::count_if(begin(nums), end(nums), isOdd);
В приведенном выше примере isOdd - это лямбда-функция, которая проверяет, является ли введенное число нечетным. Lambdas можно использовать с for_each, count_if и другими стандартными библиотечными функциями, и внезапно эти библиотеки становятся полезными с ним.
Преимущества использования лямбда-выражений заключаются в том, что их можно использовать для формирования определенной общей работы, помогает достичь параллелизма и повышает читаемость кода.
3. Алгоритмы стандартной библиотеки
Библиотека алгоритма в C ++ определяет функции, которые могут выполнять несколько операций, например сортировку, подсчет, манипулирование, поиск элементов в контейнерах и т. Д. Разработчику не нужно писать для них какой-либо код, и это экономит время, чтобы сосредоточиться на других частях. кода.
Пример стандартных библиотечных алгоритмов swap, sort и count_if приведен ниже.
//Example of Swap function for a and b int a = 5; int b = 8; swap(&a, &b); //Example of sort function. Sort elements in ascending order vector<int> v{5, 3, 4, 2, 1}; sort(v.begin(), v.end()); //Count the number of 3’s in the vector v int num_items3 = std::count_if(v.begin(), v.end(), [](int i){return i == 3;});
Можно использовать множество стандартных библиотечных алгоритмов. К преимуществам их использования относятся: они делают код более читабельным и выразительным, например, все понимают, что делает функция sort. Кроме того, отсутствие необходимости писать их с нуля экономит ваше время, усилия и всю головную боль, связанную с обработкой крайних случаев. Это также позволяет разработчику легко переключать контейнеры, поскольку большинство алгоритмов используют Итераторы для доступа к элементам. Поскольку итераторы можно использовать с любыми контейнерами, когда разработчик переходит из стека в очередь, изменения кода будут минимальными.
Самой большой проблемой для разработчика будет найти правильный алгоритм для кода и изучить его реализацию.
4. Исключения
Совершенно естественно, что программа генерирует ошибки или вызывает сбой во время выполнения. Некоторые из них могут быть предсказуемыми, некоторые - нет. Также разные типы ошибок нужно передавать по-разному. В некоторых случаях разработчик может забыть обработать случаи ошибок. Для обработки необычных и исключительных ошибок используются исключения.
Исключения в C ++ содержат 3 основных части
- Попробовать. Этот блок должен быть как можно меньше, чтобы проверить код, который выдает исключение.
- Throw - может вызывать исключения из класса std :: exception.
- Catch - блок кода, используемый для перехвата исключений. Исключения необходимо упорядочить от самых конкретных исключений вверху до общих внизу.
Пример исключения показан ниже.
//Example of Divide by Zero exception thrown void func(int a, int b) { try { if( b == 0 ) throw std::invalid_argument("b is zero"); else a/b; } catch(std::exception& e){ //Handle Exception here } }
Преимущества использования исключений заключаются в том, что между блоками try и catch объекты с локальной областью действия очищаются автоматически путем вызова их класса деструктора. Таким образом, блок finally не требуется в C ++, в отличие от других языков программирования. Также очень полезен класс std :: exception. Код большинства стандартных библиотек создает объекты, производные от этого класса. Также, когда существует цепочка вызовов функций, например a вызывает b, b вызывает c…. y вызывает z, возвращая ошибку от z обратно в a, это довольно неприятно. Это занимает много времени и влияет на производительность. В таких случаях исключения могут использоваться в z для обработки ошибок.
Таким образом, современный C ++ выразителен и удобочитаем. Это помогает разработчику использовать возможности языка для выражения намерений и минимизировать усилия, необходимые для кодирования.