rval->ref const(T), implicit conversions

tsbockman via Digitalmars-d digitalmars-d at puremagic.com
Tue Jan 19 10:14:56 PST 2016


On Tuesday, 19 January 2016 at 17:23:33 UTC, bitwise wrote:
> On Tuesday, 19 January 2016 at 06:17:17 UTC, tsbockman wrote:
>> 1) It introduces substantial template bloat, as the number of 
>> instantiations of the entire function - including the body! - 
>> scales as the square of the number of `auto ref` parameters.
>
> Your solution suffers from exactly the same problem. It still 
> uses auto ref.
>
>> 2) rvalues will be passed by value, which could be slow if the 
>> type is bulkier than `int`.
>
> No, they won't. Temporaries will be created for rvalues, and 
> lvalues will be passed by ref.

As a simple example, consider the following:

void main() {
     func(5);

     int n = 6;
     func(n);
}

Defining `func` by directly using `auto ref`, this:

void func()(auto ref int x)
{
     enum set_at_compile_time = __traits(isRef, x);
     writeln(set_at_compile_time);
}

Will be compiled into two separate functions:

void func1(int x) // pass by value
{
     writeln(false);
}

void func2(ref int x) // pass by ref
{
     writeln(true);
}

void main() {
     func1(5); // prints false

     int n = 6;
     func2(n); // prints true
}

(Try it here: http://dpaste.dzfl.pl/dc9af2059641)

Whereas using my PR:

void funcImpl(ref int x) {
     writeln(__traits(isRef, x));
}
mixin acceptRVals!("func", funcImpl);

It's effectively just one function:

void funcImpl(ref int x) {
     writeln(true);
}

void main() {
     int x = 5;
     funcImpl(x); // prints true

     int n = 6;
     funcImpl(n); // prints true
}

Note that the output IS NOT THE SAME.
(Try it yourself: http://dpaste.dzfl.pl/9ae30506b4a3)

If you don't understand why, then you have no business trying to 
dictate how the language should handle rvalues. You also don't 
fully understand why Manu's not satisfied with just using `auto 
ref` directly.



More information about the Digitalmars-d mailing list