On Sun, 2024-09-29 at 16:00 -0500, Barry Revzin via Std-Proposals wrote:


On Sun, Sep 29, 2024 at 3:32 PM Arthur O'Dwyer via Std-Proposals <std-proposals@lists.isocpp.org> wrote:
On Sun, Sep 29, 2024 at 3:26 PM Avi Kivity via Std-Proposals <std-proposals@lists.isocpp.org> wrote:
I find it common to want to constrain a range to return a particular type. Something like

    void f(std::ranges::range_of<unsigned> auto&& range_of_unsigned) { ... }

It would be trivial to define such a concept, or to forego the abbreviated template syntax and use a requires clause, but it seems to me this should be a vocabulary concept.
There's the question of whether the type should be same_as or convertible_to, perhaps there is room for two concepts here.


This sounds like the same thing (in practice) as the exposition-only container-compatible-range.


The problem with range_of is what exactly that should mean. Should range_of<unsigned> actually match any range of integral (i.e. convertible_to) or just specifically ranges of prvalue unsigned (i.e. same_as)? But same_as wouldn't even match vector<unsigned>, so if you want that did you actually want same_as but matching on value_type instead? Or decays_to?

Why would same_as not match vector<unsigned>? Of course we'd match value_type, not the range itself.



So... sure, container-compatible-range is one of those things. But the problem with range_of<T> is what exactly you wanted to check your T against.
 

We'd just have two concepts. Maybe range_of (with convertible_to matching, used for reads) and range_of_exactly (used for writes). I'd say range_of is much more useful.