C/C++ Ready | Программирование
14.5K subscribers
1.09K photos
52 videos
460 links
Авторский канал по разработке на C и C++.
Ресурсы, гайды, задачи, шпаргалки.
Информация ежедневно пополняется!

Автор: @energy_it

РКН: https://clck.ru/3QREHc

Реклама на бирже: https://telega.in/c/cpp_ready
Download Telegram
👩‍💻 Небольшой пул потоков для параллельных коротких задач!

Запускаем несколько рабочих потоков заранее, кладём задачи в общую очередь — потоки по сигналу забирают и выполняют их, без создания новых std::thread на каждую задачу.

В этой задаче:

Почувствуешь разницу между хаотичным запуском задач и порядком;

Увидишь, как несколько потоков спокойно делят очередь;

Замечаешь, как код берёт рутину выбора на себя.


Покажет использование в main и почему порядок вывода «плавает». Добавление std::future сделает пул ещё удобнее.

📣 C++ Ready | #задача
Please open Telegram to view this post
VIEW IN TELEGRAM
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥20👍107🤝1
49😁23🔥15👎6
Безопасный union — std::variant и std::visit!

Обычный union в C++ легко приводит к UB: нужно самому следить, какой тип там сейчас хранится. std::variant из стандарта делает то же самое, но безопасно: внутри хранится ровно один из перечисленных типов и следит за активным вариантом.

Сначала объявим удобный псевдоним для значения, которое может быть int, double или std::string:
using Value = std::variant<int, double, std::string>;


Теперь напишем функцию-обработчик, которая по-разному реагирует на каждый возможный тип внутри Value с помощью std::visit:
void handle(const Value& v) {
std::visit([](const auto& x) {
using T = std::decay_t<decltype(x)>;

if constexpr (std::is_same_v<T, int>) {
std::cout << "int: " << x << "\n";
} else if constexpr (std::is_same_v<T, double>) {
std::cout << "double: " << x << "\n";
} else {
std::cout << "string: " << x << "\n";
}
}, v);
}


И маленький пример использования: одно и то же значение по очереди становится разными типами, а std::visit всегда вызывается с актуальным вариантом:
int main() {
Value v = 42;
handle(v); // int: 42

v = 3.14;
handle(v); // double: 3.14

v = std::string("hello");
handle(v); // string: hello

return 0;
}


🔥 std::variant + std::visit дают безопасный, типобезопасный union и аккуратную обработку нескольких типов без кастов и ручного трекинга «какой тип лежит внутри».

📣 C++ Ready | #практика
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥11👍96👎4🤝1
👩‍💻 Строки, которые форматируются как надо!

Когда вывод разбросан по cout и printf, его трудно менять; удобнее собрать текст по шаблону и лишь подставлять нужные значения.

В этом гайде:

Посмотрим, как собирать аккуратный текст из значений;

Разберём примеры выравнивания и красивых табличных чисел;

Сделаем простой и понятный лог без склейки строк.


Освоив такой подход, вы сможете держать формат текста в одном месте и менять его без боязни сломать вывод.

📣 C++ Ready | #гайд
Please open Telegram to view this post
VIEW IN TELEGRAM
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥1413🤝9👍2
This media is not supported in your browser
VIEW IN TELEGRAM
☕️ LangShift — учись новому языку программирования, используя знания, которые у тебя уже есть!

Этот сайт предлагает другой путь: выбираешь язык, который уже знаешь, и переходишь на новый через сопоставление синтаксиса и парадигм. Более 80 модулей, 30+ проектов, всё бесплатно и без регистрации.

📌 Оставляю ссылочку: langshift.dev

📣 C++ Ready | #ресурс
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥14👍128
👩‍💻 Одна строка против мусора в контейнерах!

Иногда половина функции уходит на то, чтобы выкинуть лишние элементы; удобнее выразить эту уборку одной понятной строкой с явным правилом.

В этом посте:
Разберём, как удалять ненужное без ручных циклов;

Покажем, как упростить сложные правила фильтрации коллекций;

Поймём, как сделать очистку данных визуально очевидной.


Когда уборка в коллекциях превращается в одну строку, читать и изменять такой код становится проще и спокойнее.

📣 C++ Ready | #гайд
Please open Telegram to view this post
VIEW IN TELEGRAM
Please open Telegram to view this post
VIEW IN TELEGRAM
🔥1610👍5🤝1
DBG-макрос на std::source_location: удобно дебажим выражения с контекстом

Иногда хочется быстро подсмотреть значение переменной, а не протаскивать логгер, не ставить точку останова и не писать std::cout << ... руками.

Давайте сделаем простой DBG(expr), который в debug-сборке печатает:
• само выражение;
• его значение;
• файл, строку и функцию, где это произошло.

В релизе же макрос превратится в пустышку и не повлияет на производительность.

Подключаем заголовки:
#include <iostream>
#include <string_view>
#include <source_location>


Сделаем вспомогательную функцию debug_print, которая принимает значение, текст выражения и информацию о месте вызова:
template <typename T>
void debug_print(const T& value,
std::string_view expr,
const std::source_location& loc = std::source_location::current())
{
std::cerr << "[DBG] " << expr << " = " << value << "\n"
<< " at " << loc.file_name() << ":" << loc.line()
<< " in " << loc.function_name() << "\n";
}


Теперь объявим макрос DBG, который работает только в debug-сборке (пока не определён NDEBUG):
#ifndef NDEBUG
#define DBG(expr) debug_print((expr), #expr)
#else
#define DBG(expr) ((void)0)
#endif


Проверим на простом примере:
#include <vector>

int main() {
int x = 42;
std::vector<int> v{1, 2, 3};

DBG(x);
DBG(v.size());
DBG(v[1] + x);

return 0;
}


При запуске debug-сборки увидим что-то вроде:
[DBG] x = 42
at example.cpp:8 in main
[DBG] v.size() = 3
at example.cpp:9 in main
[DBG] v[1] + x = 44
at example.cpp:10 in main


А в релизной сборке (-DNDEBUG) все вызовы DBG(...) тихо исчезнут на этапе компиляции.

🔥 В итоге у тебя есть удобный DBG-макрос на чистом стандарте C++20: в отладке он показывает выражения с контекстом (файл, строка, функция), а в релизе не оставляет ни следа в бинарнике.

📣 C++ Ready | #практика
Please open Telegram to view this post
VIEW IN TELEGRAM
👍20🔥128
👩‍💻 Консольный таймер обратного отсчёта за пару строк кода!

Просим пользователя ввести количество секунд, красиво форматируем их в вид мм:сс и плавно считаем вниз до нуля, обновляя одну строку в консоли и подавая сигнал, когда время истекает.

В этой задаче:

Потренируешь работу с std::chrono и паузами в одну секунду;

Увидишь, как перерисовывать таймер в одной строке с помощью \r и std::flush;

Соберёшь удобный маленький инструмент, который можно встроить в любую консольную утилиту.


По ходу дела аккуратно обработаем ввод, вынесем форматирование времени в отдельную функцию и посмотрим, как легко из простого цикла сделать полезный таймер.

📣 C++ Ready | #задача
Please open Telegram to view this post
VIEW IN TELEGRAM
Please open Telegram to view this post
VIEW IN TELEGRAM
👍21🔥1310