type5 is much more first principles based, so we get a lot of weird quirks removed: - FromLiteral no longer needs to understand AST - Type unifications works more like Haskell - Function types are just ordinary types, saving a lot of manual busywork and more.
44 lines
1.1 KiB
Python
44 lines
1.1 KiB
Python
from .record import Record
|
|
from .typeexpr import (
|
|
AtomicType,
|
|
TypeApplication,
|
|
TypeConstructor,
|
|
TypeExpr,
|
|
TypeVariable,
|
|
)
|
|
|
|
|
|
class TypeRouter[T]:
|
|
def when_atomic(self, typ: AtomicType) -> T:
|
|
raise NotImplementedError(typ)
|
|
|
|
def when_application(self, typ: TypeApplication) -> T:
|
|
raise NotImplementedError(typ)
|
|
|
|
def when_constructor(self, typ: TypeConstructor) -> T:
|
|
raise NotImplementedError(typ)
|
|
|
|
def when_record(self, typ: Record) -> T:
|
|
raise NotImplementedError(typ)
|
|
|
|
def when_variable(self, typ: TypeVariable) -> T:
|
|
raise NotImplementedError(typ)
|
|
|
|
def __call__(self, typ: TypeExpr) -> T:
|
|
if isinstance(typ, AtomicType):
|
|
if isinstance(typ, Record):
|
|
return self.when_record(typ)
|
|
|
|
return self.when_atomic(typ)
|
|
|
|
if isinstance(typ, TypeApplication):
|
|
return self.when_application(typ)
|
|
|
|
if isinstance(typ, TypeConstructor):
|
|
return self.when_constructor(typ)
|
|
|
|
if isinstance(typ, TypeVariable):
|
|
return self.when_variable(typ)
|
|
|
|
raise NotImplementedError(typ)
|