Binding rvalues to ref parameters redux

Timon Gehr timon.gehr at gmx.ch
Wed Mar 27 16:19:20 UTC 2019


On 27.03.19 02:38, Andrei Alexandrescu wrote:
> Work has been underway on redoing DIP 1016. I haven't made a pull 
> request yet as it's a bit early. Looking for high-level observations:
> 
> https://gist.github.com/andralex/e5405a5d773f07f73196c05f8339435a
> 
> Thanks in advance for any feedback.

Assuming that we don't add a new function parameter storage class, I 
think this DIP gets the semantics exactly right. However, I would 
explain the following two things:

- Currently, the main use case of disallowed rvalue-ref calls is to 
check whether a (templated) function may change your argument using 
`ref` by trying to call it with an rvalue inside `__traits(compiles, 
...)`. Maybe the DIP could state that even though this use case breaks, 
after this change, the functionality is in fact still available, but 
instead of an rvalue, you use an overload set containing a property 
getter and a property setter. (This is in fact a backwards-compatible 
way to do it.)

- It may not be immediately obvious that the DIP does not break 
overloading of ref and non-ref. [1]  The reason why overloading does not 
break is that a non-ref function may be called with a property getter 
that also has a setter, while the ref overload may not, so `ref` would 
keep being more specialized. [2]


However, I think adding a new storage class that documents that `ref` is 
being used for efficiency rather than for (shallow) modification, and 
restricting the rvalue rewrite to such parameters may make D code more 
readable, and it will make introspection more effective, because trying 
to call a function with an rvalue will query intent to modify. 
Additionally, it would avoid code breakage.

But of course, this means we would have two kinds of `ref` arguments, 
one that accepts lvalues and one that accepts both lvalues and rvalues, 
and the obvious next step would be to add `ref` arguments that only 
accept rvalues. :o)


[1] In my own frontend, if implemented without also changing the 
overloading logic, `ref` would no longer be more specialized than non-ref.

[2] In my frontend, the most restricted kind of expression that matches 
a non-ref argument (used to try to call the other function to determine 
specialization) is currently an rvalue of the respective type, after 
this change it would need to be an overload set of property getter and 
setter.


More information about the Digitalmars-d mailing list