What is the benefit of using universal references in a range based loop?
I've seen code like this many times:
template<typename Collection>
void Foo(Collection&& c)
{
for (auto&& i : std::forward<Collection>(c))
// do something with i
}
For all containers, STL (except vector<bool>
) i
has an lvalue reference type. Is there any practical sense to introduce auto&&
in this case?
source to share
As you said, a perfect example of where you don't have an lvalue is std::vector<bool>
. Usage auto&
will not compile because pr is returned from the iterator.
Also, I sometimes had to do ranges that didn't return an lvalue from its iterator.
Also, the potential for use auto&&
is that there are no cases where it won't work. Even you have a weird case where your iterator gives a const rvalue reference auto&&
binds to it.
It's also easier for learning to say "use auto&&
in your loops". because it won't copy and run all over the place.
Where it also suggests to allow implicit auto&&
and include syntax for (x : range)
(I can't remember which one it is. If you know that, tell me in the comments)
source to share