I have an abstract class, Float, that generates concrete subclasses dynamically. I would like to type-hint the return type so that the IDE knows that it’s a concrete subtype of Float. That is, when you create a Float16 class, an a_float16 object has the expected autocompletes because the IDE understands what Float16 should have.
To add an additional wrinkle, there is what essentially amounts to a flag (not as literally as below) such that one version of the return types has a few extra mixin details. This could easily be separated into two methods, however, if this is the sticky issue.
class Float(BitType): # BitType is an ABC
def specialize(*args, **kwargs, flag: bool
) -> ???:
if flag:
class ConcreteFloat(Float, AutoDetails):
... # Concrete implementation
else:
class ConcreteFloat(Float):
... # Concrete implementation
... # Set the name of ConcreteFloat to whatever was provided
return ConcreteFloat
Float16 = Float.specialize(
num_exponent_bits_=5,
num_mantissa_bits_=10,
packing_format_letter_="e",
name_="Float16"
)
a_float16 = Float16(5.0) # Type-hinter should know that this is a concrete subclass of Float
What is the best way to go about doing this (or some options around this)?
Currently considered options:
Type-hinting the return value of type[Float] just makes the IDE complain that the return value is an abstract class with nonconcrete details.
Using a metaclass feels like it could get complicated, but I’m open to it (there are also other types, though. UInt/SInt deriving from Int each with their own dynamic concrete subtype creation methods, a CharArray class, and a Buffer class with the same).
Type-hinting the return value of type[Float] just makes the IDE
complain that the return value is an abstract class with nonconcrete
details.
Reloading the IDE removed this issue. This works well.