bug with std.range.zip? range with opEquals(const) const not allowed inside zip

Jens Mueller jens.k.mueller at gmx.de
Mon Aug 27 00:42:34 PDT 2012


Jonathan M Davis wrote:
> On Sunday, August 26, 2012 14:47:38 Jens Mueller wrote:
> > What is the ref situation?
> > I thought ref is used as an optimization that allows passing lvalues
> > more efficiently whereas without ref is needed for rvalues.
> 
> ref doesn't necessarily have anything to do with optimizations. It makes it so 
> that any operations done on the function parameter inside the function are 
> also done on the variable passed in. The parameter is essentially an alias for 
> the variable passed in.
> 
> You can choose to use ref in order to avoid a copy, but it's also arguably bad 
> practice to have a function take an argument by ref if it's not actually going 
> to mutate the original, since that's confusing.
> 
> _const_ ref is more for avoiding the copy, since it's like ref except that you 
> can't actually mutate the variable. So, it makes sense to use const ref 
> specifically to avoid unnecessary copies.

This is what I meant.

> However, while in C++, you can pass rvalues to const&, in D, you can't. It 
> doesn't matter if the ref is const or not, it still requires an lvalue. This 
> solves certain issues caused by C++'s choice (issues primarily related to 
> function overloading IIRC), but it makes it rather difficult to declare a single 
> function which takes either an lvalue or an rvalue but which tries to avoid 
> unnecessary copying.
> 
> D's auto ref essentially does it (rvalues are then always passed by rvalue and 
> lvalues are always passed by lvalue), but it only works with templates, 
> because it has to create two versions of the function.
>
> So, what we'd _like_ to have is a solution where you can mark a parameter in a 
> way similar to auto ref or C++s const& and have the function not care whether 
> it's passed an lvalue or rvalue and have it avoid copying as much as possible 
> and have it work with _all_ function types, not just templated ones, but we 
> haven't sorted out how to do that yet. _That's_ the ref situation that needs 
> to be solved.

Aha. I see.
Then we get down from four declarations to two by writing
bool opEquals(const auto ref S rhs) const {...}
and
bool opEquals(auto ref S rhs) {...}

And with inout probably even further:
bool opEquals(inout auto ref S rhs) inout {...}

Thanks for explaining.

Jens


More information about the Digitalmars-d mailing list