Ranges-библиотека умеет не только фильтровать и трансформировать, но и разбивать диапазоны на части. Разберём три инструмента — каждый для своей задачи.
🍴 views::split — разбивка по разделителю
std::string csv = "один,два,три,четыре";
// Разбиваем по запятой
for (auto part : csv | views::split(',')) {
// part — под-диапазон символов, не строка
// В C++20 явно конструируем string:
std::cout << std::string(part.begin(), part.end()) << "\n";
}
// один
// два
// три
// четыре
В C++23 появился
std::ranges::to, и конвертация стала лаконичнее:for (auto part : csv | split(',')) {
std::cout << std::ranges::to<std::string>(part) << "\n";
}❗️
views::split возвращает под-диапазоны, а не строки — явное преобразование обязательно в обоих стандартах.🥨 views::chunk(n) — разбивка на блоки фиксированного размера (C++23)
std::vector<int> data = {1, 2, 3, 4, 5, 6, 7};
for (auto chunk : data | views::chunk(3)) {
for (int x : chunk) std::cout << x << " ";
std::cout << "\n";
} /
/ 1 2 3
// 4 5 6
// 7❗️ Если размер диапазона не делится на n нацело — последний блок содержит оставшиеся элементы.
🍪 views::chunk_by — разбивка по условию (C++23)
Группирует соседние элементы, пока выполняется предикат между двумя соседями.
std::vector<int> v = {1, 1, 2, 3, 3, 3, 4, 4};
// Группируем подряд идущие равные элементы
for (auto group : v | views::chunk_by(std::equal_to{})) {
for (int x : group) std::cout << x << " ";
std::cout << "| ";
} /
/ 1 1 | 2 | 3 3 3 | 4 4 |
// Вариант с std::equal_to<>{} — лаконичнее:
for (auto group : v | chunk_by(std::equal_to<>{})) { ... }❗️ Предикат принимает два соседних элемента — новая группа начинается там, где он вернул false.
📍Навигация: Вакансии • Задачи • Собесы
Библиотека C/C++ разработчика
#константная_правильность