HaxeFoundation / haxe-evolution

Repository for maintaining proposal for changes to the Haxe programming language
111 stars 58 forks source link

Extension of abstracts #109

Open EliteMasterEric opened 1 year ago

EliteMasterEric commented 1 year ago

Rendered proposal

back2dos commented 1 year ago

I'm not sure I understand the use case fully. But for what's explained, users could easily just use static extensions to add functionality. Or @:forward abstract Baz(Bar) { /* added functionality here */}.

FWIW I think we should rather look into allowing abstracts to extends abstracts, as subtyping abstracts is a relatively tedious endeavour. I've become used to model things in a way that I can avoid the need, but I think it's a rather arbitrary limitation, that should not be that hard to lift.

Haven't fully thought this through, but I would say an abstract should be allowed to extend another, under the restriction that the underlying type must be a subtype of the underlying type of the abstract that is being extended.

class BaseData {}
class SpecialData extends BaseData {}

abstract Base(BaseData) {
  public function doBasicThing() {}
}

abstract Special(SpecialData) extends Base {// underlying type could also be BaseData
  public function doSpecialThing() {}
}
// this would allow for
var s:Special = ...;
s.doBasicThing();

In essence, the above declaration of Special would correspond to this:

abstract Special(SpecialData) to Base {// the compiler won't allow this incompatible cast, but let's assume it could
  public function doBasicThing() (abstract:Base).doBasicThing();
  public function doSpecialThing() {}
}

So among other things Special is a subtype of Base and all methods of Base are available via Special as well.

Then again, I'm not even sure that doing something of this sort addresses the original use case.

EliteMasterEric commented 1 year ago

users could easily just use static extensions to add functionality

I may have to test how convenient static extensions are for my use case.