range-v3 icon indicating copy to clipboard operation
range-v3 copied to clipboard

string_view support

Open DarthGandalf opened this issue 5 years ago • 3 comments

With 0.10.0 this compiles:

std::string_view input;
auto x = input | ranges::views::split('\n') | ranges::views::filter([](const std::string& line) { return true; });

but this does not:

auto x = input | ranges::views::split('\n') | ranges::views::filter([](std::string_view line) { return true; });
/home/somebody/advent-of-code/2020/day2.cpp:42:47: error: invalid operands to binary expression ('ranges::split_view<std::__1::basic_string_view<char, std::__1::char_traits<char>>, ranges::single_view<char>>' and 'ranges::views::view_closure<ranges::detail::bind_back_fn_<ranges::views::filter_base_fn, (lambda at /home/somebody/advent-of-code/2020/day2.cpp:42:71)>>')
                auto x = input | ranges::views::split('\n') | ranges::views::filter([](std::string_view line) { return true; });
                         ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/usr/include/c++/v1/cstddef:94:17: note: candidate function not viable: no known conversion from 'ranges::split_view<std::__1::basic_string_view<char, std::__1::char_traits<char>>, ranges::single_view<char>>' to 'std::byte' for 1st argument
constexpr byte  operator| (byte  __lhs, byte __rhs) noexcept
                ^
/usr/include/range/v3/view/any_view.hpp:65:24: note: candidate function not viable: no known conversion from 'ranges::split_view<std::__1::basic_string_view<char, std::__1::char_traits<char>>, ranges::single_view<char>>' to 'ranges::category' for 1st argument
    constexpr category operator|(category lhs, category rhs) noexcept
                       ^
/usr/include/c++/v1/bitset:1071:1: note: candidate template ignored: could not match 'bitset' against 'split_view'
operator|(const bitset<_Size>& __x, const bitset<_Size>& __y) _NOEXCEPT
^
/usr/include/range/v3/view/view.hpp:116:17: note: candidate template ignored: constraints not satisfied [with Rng = ranges::split_view<std::__1::basic_string_view<char, std::__1::char_traits<char>>, ranges::single_view<char>>, ViewFn = ranges::detail::bind_back_fn_<ranges::views::filter_base_fn, (lambda at /home/somebody/advent-of-code/2020/day2.cpp:42:71)>]
                operator|(Rng && rng, view_closure<ViewFn> vw)
                ^
/usr/include/range/v3/view/view.hpp:114:28: note: because 'defer::invocable_view_closure<ranges::detail::bind_back_fn_<ranges::views::filter_base_fn, (lambda at /home/somebody/advent-of-code/2020/day2.cpp:42:71)>, ranges::split_view<std::__1::basic_string_view<char, std::__1::char_traits<char> >, ranges::single_view<char> > >' evaluated to false
                    defer::invocable_view_closure<ViewFn, Rng>) //
                           ^
/usr/include/concepts/concepts.hpp:284:27: note: expanded from macro 'CPP_template'
    template<__VA_ARGS__> CPP_PP_EXPAND                                         \
                          ^
/usr/include/range/v3/view/view.hpp:82:31: note: because 'ranges::invocable_view_closure<ranges::detail::bind_back_fn_<ranges::views::filter_base_fn, (lambda at /home/somebody/advent-of-code/2020/day2.cpp:42:71)>, ranges::split_view<std::__1::basic_string_view<char, std::__1::char_traits<char> >, ranges::single_view<char> > >' evaluated to false
            CPP_defer(ranges::invocable_view_closure, ViewFn, Rng);
                              ^
/usr/include/range/v3/view/view.hpp:75:9: note: because 'invocable<ranges::detail::bind_back_fn_<ranges::views::filter_base_fn, (lambda at /home/somebody/advent-of-code/2020/day2.cpp:42:71)>, ranges::split_view<std::__1::basic_string_view<char, std::__1::char_traits<char> >, ranges::single_view<char> > >' evaluated to false
        invocable<ViewFn, Rng> &&
        ^
/usr/include/range/v3/functional/concepts.hpp:33:13: note: because 'invoke(((decltype(fn) &&)fn), std::declval<Args>()...)' would be invalid: no matching function for call to object of type 'const ranges::invoke_fn'
            invoke(CPP_fwd(fn), std::declval<Args>()...)
            ^
/usr/include/concepts/concepts.hpp:189:5: note: expanded from macro 'CPP_requires'
    CPP_requires_n(CPP_PP_COUNT(__VA_ARGS__), __VA_ARGS__)
    ^
/usr/include/concepts/concepts.hpp:208:9: note: expanded from macro 'CPP_requires_n'
        CPP_valid_expressions
        ^
/usr/include/range/v3/view/view.hpp:141:35: note: candidate template ignored: could not match 'view_closure' against 'split_view'
            friend constexpr auto operator|(view_closure<ViewFn> vw, Pipeable pipe)
                                  ^
/usr/include/range/v3/view/view.hpp:157:13: note: candidate template ignored: constraints not satisfied [with Rng = ranges::split_view<std::__1::basic_string_view<char, std::__1::char_traits<char>>, ranges::single_view<char>>, ViewFn = ranges::detail::bind_back_fn_<ranges::views::filter_base_fn, (lambda at /home/somebody/advent-of-code/2020/day2.cpp:42:71)>]
            operator|(Rng &&, view_closure<ViewFn> const &) // ******* READ THIS ********
            ^
/usr/include/range/v3/view/view.hpp:161:22: note: because '!viewable_range<ranges::split_view<std::__1::basic_string_view<char, std::__1::char_traits<char> >, ranges::single_view<char> > >' evaluated to false
                    (!viewable_range<Rng>)) = delete;       // **************************
                     ^
/usr/include/concepts/concepts.hpp:414:17: note: expanded from macro 'CPP_ret'
    __VA_ARGS__ CPP_PP_EXPAND                                                   \
                ^
1 error generated.

Probably because there's no constructor of string_view which accepts begin/end iterators. But split() returns contiguous memory chunks, doesn't it?

DarthGandalf avatar Dec 02 '20 10:12 DarthGandalf

Unfortunately, no, split() returns input iterator only :( I recently stucked with same issue, and found an article about this problem: https://brevzin.github.io/c++/2020/07/06/split-view/ . @BRevzin sorry for mentioning you, but maybe you may help with this issue. As of that I think about the problem in general that we must make a Defect Report paper to WG21 about this inconvenient view in C++20 (with title like "don't demote ranges to input ranges", it needs bikeshedding 😊 ) and try to fix it in @ericniebler 's range-v3 lib.

leha-bot avatar Dec 03 '20 11:12 leha-bot

maybe thid: https://brevzin.github.io/c++/2020/07/06/split-view/

On Thu, 3 Dec 2020 at 13:32, Alex [email protected] wrote:

Unfortunately, no, split() returns input iterator only :( I recently stucked with same issue, and found an article about this problem (but lost link 😢 ) with title like "improving ranges::views::split() with std::string_view"

— You are receiving this because you are subscribed to this thread. Reply to this email directly, view it on GitHub https://github.com/ericniebler/range-v3/issues/1584#issuecomment-737884999, or unsubscribe https://github.com/notifications/unsubscribe-auth/AB2ORDN7BQHQIJKJOVWGIVDSS5ZN3ANCNFSM4UKJCVKQ .

dvirtz avatar Dec 03 '20 13:12 dvirtz

It's not input-only, it's forward-only. See P2210.

brevzin avatar Dec 03 '20 14:12 brevzin