Как сплитнуть строку с помощью std::ranges?
Пытаюсь сплитнуть строки с помощью std::ranges.
const std::string path = "/path/1/2/sda";
for (auto& token : path | std::ranges::views::split("/")){
std::cout << token << std::endl;
}
Но компилятор выдает две ошибки
In template: no matching function for call to '__ranges_begin'
Invalid operands to binary expression ('const std::string' (aka 'const basic_string<char>') and 'std::ranges::views::__adaptor::_RangeAdaptorClosure<(lambda at /usr/include/c++/10/ranges:1135:7)>')
Использую gcc10, включе 20 стандарт.
Ответы (1 шт):
Ну что же сделаешь, нам в плюсы фичи подвозят, а удобство использования - нет. В случае range их там было 3 или 4 варианта, гнались за минимальным использованием памяти и по дороге потеряли банальное удобство.
ranges::views::split возвращает ещё один "диапазон", который нужно конвертнуть в то, что мы на самом деле ожидаем. То есть, говоря по простому, split возвращает пару переменных, которые идентифицируют начало и конец найденного элемента, но в очень общем виде. Поэтому и нужно сделать финальный штрих - конвертировать в нужное.
Вот работающий пример (как минимум у меня на gcc 10.2.0 + -std=c++20 собралось)
#include <iostream>
#include <string>
#include <ranges>
#include <string_view>
using namespace std;
int main()
{
const std::string path = "/path/1/2/sda";
auto view = path
| ranges::views::split('/')
| ranges::views::transform([](auto &&rng) {
return std::string_view(&*rng.begin(), ranges::distance(rng));
});
for (const auto& token : view){
std::cout << token << std::endl;
}
}
А вот человек об этом рассуждает https://brevzin.github.io/c++/2020/07/06/split-view/
А вот связанный вопрос https://stackoverflow.com/questions/48402558/how-to-split-a-stdstring-into-a-range-v3-of-stdstring-views - но только там видимо очень старый вариант.