Discussion Thread: DIP 1042--ProtoObject--Community Review Round 1

Adam D Ruppe destructionator at gmail.com
Tue Jan 11 16:34:29 UTC 2022

On Tuesday, 11 January 2022 at 12:48:00 UTC, WebFreak001 wrote:
> I partly agree with this, forcing attributes in the interface 
> is most painfully for the programmer.

Yeah, if you have a flexible interface, implementations can 
always tighten it, but you can't go the other way around.

The good news is you can use @trusted on an implementation to 
bridge the gap.

> However this alone would fall short here if standard library 
> stuff would suddenly use interfaces to accept arguments:
> ```d
> void sort(Ordered[] objects);
> ```

Yeah, best you can do is to template it or offer overloads. Kinda 
like the status quo with opApply... but you could do like

void sort(Ordered[] objects) { impl }

void sort(SafeOrdered[] safeObjects) @trusted {
    sort(cast(Ordered[]) safeObjects);

That's not too terrible but just like with opApply if you wanna 
do nogc and pure and friends too, the combinations multiply out 
pretty quickly. Templating it on the most derived common type can 
solve this... but it is still a little bit tricky to do the 
proper introspection to cast to the correct attributes when you 
forward to the un-attributed function (like the `@trusted` in the 
example). Some reflection code could probably do it....

void sortImpl(Ordered[] objects) {}

void sort(T)(T objects) {

auto conditionalForward(alias toWhat, T...)(T args) {
    // only worried about the actual impelmentation of the things 
actually in the interface
    static if(AllSatisfy!isNoGc, commonMethods!(Parameters!toWhat, 
         return cast(@nogc) toWhat(args);
    else static if(pure && nogc)
    else static if(pure)
    else static if (all the combinations)

What an ugly af conditionalForward, but such a thing should be 

Of course whether you'd gain much in terms of compile speed 
benefits etc using the dynamic dispatch after doing all that 
reflection would need tests. I'm not sure. It would at least 
reduce to a single instance of the actual sort function in the 
binary so I actually think it *would* come out ahead. Assuming 
users ok with dynamic dispatch anyway.

The fact is there's just some conflict between the static 
verification attributes provide and the dynamic dispatch 
interfaces provide. You CAN bridge it over, but there's just some 
fundamental conflict between them.

The DIP doesn't address this conflict. It just discards the 
current flexibility entirely in actual practice. Worth noting if 
you want to discard the current flexibility entirely, you can do 
that today in a child class. Remember, you're always allowed to 
tighten requirements in subtypes.

More information about the Digitalmars-d mailing list