I recently discovered the ranges stdandard library and encountered a strange behavior. When chaining multiple range adaptors, I can't chain after using std::ranges::views::join
:
vec | std::ranges::views::slide(2) | std::ranges::views::join
works as intended, but
vec | std::ranges::views::slide(2) | std::ranges::views::join | std::ranges::views::slide(2)
will result in compilation error:
error: no match for 'operator|' (operand types are 'std::ranges::join_view<std::ranges::slide_view<std::ranges::ref_view<std::vector<int> > > >' and 'std::ranges::views::__adaptor::_Partial<std::ranges::views::_Slide, int>')
265 | vec | std::ranges::views::slide(2) | std::ranges::views::join | std::ranges::views::slide(2);
| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ ^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~
| | |
| | std::ranges::views::__adaptor::_Partial<std::ranges::views::_Slide, int>
| std::ranges::join_view<std::ranges::slide_view<std::ranges::ref_view<std::vector<int> > > >
Why is that? and what do I have to do to make multiple joins work?
Thanks in advance!
slide_view
requires forward_range
since the elements need to be traversed more than once.
This is not the case for join_view
in your case, because the latter joins a nested range whose elements are prvalue ranges (slide_view
acts on vector
will produce a range whose element type is prvalue span
as "window"), which makes it just an input_range
.
The constraints are not satisfied so compilation fails.