Reputation: 711
Otherwise, size(t) converted to its decayed type, if ranges::disable_sized_range<std::remove_cv_t<T>> is false, and the converted expression is valid and has an integer-like type, where the overload resolution is performed with the following candidates:
void size(auto&) = delete;
void size(const auto&) = delete;
1
class Test {
friend size_t size(/*const*/ Test&) {
return 0;
}
};
int main() {
std::ranges::size(Test{});
// no matching function error when adding the `const` qualifier
}
https://godbolt.org/z/79e5vrKrT
Generally, size
method doesn't require to modify the range, like what std::size
does.
Why is there such a constraint of std::ranges::size
? (Seems it's only performed for non-member version.)
Upvotes: 7
Views: 1582
Reputation: 42776
Why is there such a constraint of
std::ranges::size
? (Seems it's only performed for non-member version.)
Although the size
method does not modify the range, some ranges do not have a const
-qualified member begin()
, which allows only non-const
-qualified objects to model a range
.
This also makes some range adaptors in the standard may only have a non-const
-qualified size
.
For your example, considering that Test
only has non-const
begin
/end
or size
, then friend size_t size(Test&)
can really only be the option.
Upvotes: 3