range-v3: объединение диапазонов с разделителем

Я пытаюсь создать базовую демонстрацию библиотеки range-v3: взять несколько целых чисел, отфильтровать нечетные значения, преобразовать их в строки, а затем объединить их в список, разделенный запятыми. Например, { 8, 6, 7, 5, 3, 0, 9 } становится "8, 6, 0". Из чтения документов и изучения примеров можно сделать вывод, что наивное решение напоминать:

string demo(const vector<int>& v)
{
    return v |
        ranges::view::filter([](int i) { return i % 2 == 0; }) |
        ranges::view::transform([](int i) { return to_string(i); }) |
        ranges::view::join(", ");
}

но построение на Clang 7 завершается с ошибкой со статическим утверждением, что «Невозможно получить представление о временном контейнере». Поскольку я собираю результат в строку, вместо этого я могу использовать нетерпеливую версию — action::join:

string demo(const vector<int>& v)
{
    return v |
        ranges::view::filter([](int i) { return i % 2 == 0; }) |
        ranges::view::transform([](int i) { return to_string(i); }) |
        ranges::action::join;
}

но нетерпеливая версия, похоже, не имеет перегрузки, которая принимает разделитель.

Интересно, что исходное утверждение исчезнет, ​​если вы сначала соберете входные данные join в контейнер. Следующее компилируется и работает нормально:

string demo(const vector<int>& v)
{
    vector<string> strings = v |
        ranges::view::filter([](int i) { return i % 2 == 0; }) |
        ranges::view::transform([](int i) { return to_string(i); });
    return strings | ranges::view::join(", ");
}

но это полностью противоречит принципу ленивых вычислений, который так сильно влияет на библиотеку.

Почему первый пример не работает? Если это невозможно, можно ли указать action::join разделитель?


person Matt Kline    schedule 27.03.2019    source источник
comment
На первый взгляд этот вопрос напоминает stackoverflow.com/q/48383671, но, похоже, здесь возникают другие проблемы. ranges::to_<string> не решает эту проблему.   -  person Matt Kline    schedule 28.03.2019
comment
Почему бы вам не вернуть auto вместо строки? Это позволит вам сделать его по-настоящему ленивым.   -  person bartop    schedule 28.03.2019
comment
Вы бы, конечно, за пределами демо, как это, но это только делает статическое утверждение где-то еще. В конце концов вы захотите собрать результат в строку (для ввода-вывода или хранения в другой структуре), и он сработает там.   -  person Matt Kline    schedule 28.03.2019


Ответы (1)


action::join должен принимать разделитель. Не стесняйтесь подавать запрос функции. Действия требуют большой любви.

person Eric Niebler    schedule 28.03.2019
comment
Куда мы можем отправить запрос функции? - person einpoklum; 20.11.2020