Const ref and rvalues again...

foobar foo at bar.com
Thu Oct 18 02:50:33 PDT 2012


On Thursday, 18 October 2012 at 06:11:26 UTC, monarch_dodra wrote:
> On Thursday, 18 October 2012 at 04:30:17 UTC, Jonathan M Davis 
> wrote:
>> On Thursday, October 18, 2012 06:24:08 jerro wrote:
>>> What would be the problem with const ref taking rvalues?
>>
>> Read the thread that I already linked to:
>>
>> http://forum.dlang.org/thread/4F84D6DD.5090405@digitalmars.com
>>
>> - Jonathan M Davis
>
> I read the thread, and not a single one of the "problematic 
> cases" are actually valid C++.
>
> Yes: the faulty MSVC has taught people to do retarded things, 
> or be afraid of things that were illegal to begin with (in 
> particular, pass an rvalue to a ref, WHICH IS ILLEGAL IN C++), 
> such as "increment(5)".
>
> There is actually nothing wrong with creating a temporary when 
> something is bound to a const ref, provided the compiler 
> follows the rules:
>
> *Only LValues with an EXACT type match may be passed to a 
> reference.
> *In regards to *const* references, RValues may be copied in a 
> temporary, and that temporary bound the the ref.
>
> I'm not saying we particularly *need* this in D (C++ has a "by 
> ref" paradigm that makes it more important, but D *rarelly* 
> ever passes by const ref).
>
> But if the compiler respects the above two rules (which it 
> should), then RValue to const ref is both perfectly doable and 
> safe (as safe as refs get anyways).

By allowing the the C++ semantics the function looses semantic 
information - whether the actual parameter was lvalue or rvalue. 
This semantic info can be used bot for compiler optimizations and 
move semantics. This is the reason C++11 added && references.

General question (might not be relevant to current design of D):
How about leaving the decision to the compiler and let the 
programmer only specify usage intent?
E.g.: (I'm speaking semantics here, not syntax)
void foo(const Type t); // 1. I only read the value
void foo (mutate Type t); // 2. I want to also mutate the actual 
parameter
void foo (move Type t); // 3. I want to move the actual parameter

In case 1 above, the compiler is free to pass lvalues by const& 
and rvalues by value or perhaps optimize above certain size to 
const& too.
In case 2, the compiler passes a ref to lvalue, rvalues are not 
accepted at CT.
If I want move semantics, I can use option 3 which accepts 
rvalues by ref. btw, what's the correct semantics for lvalues 
here?

What do you think?


More information about the Digitalmars-d mailing list