Open ghost opened 2 months ago
Alternatively: Some way to turn the typeclass dictionary into a value, pass it to (lisp), and call a typeclass-based method using it. Both approaches could make sense to implement, even together.
Or turn any type into a value and let (coalton) accept it as an optional parameter.
To add to this, the following block compiles,
(coalton-toplevel
(define (check-num x)
((fn (x) (+ x x)) (lisp :a (x) x))))
but this block does not,
(coalton-toplevel
(define (check-eq x)
((fn (x) (== x x)) (lisp :a (x) x))))
erroring instead with,
error: Ambiguous predicate
--> repl:4:8
|
4 | (== X X))
| ^^ Ambiguous predicate EQ :A
[Condition of type COALTON-IMPL/TYPECHECKER/BASE:TC-ERROR]
Maybe the inferences applied to the Num
type class can be generalized under the hood.
For what it's worth, I implemented an interface between types and classes defined in Lisp and in Coalton in order to hook my Coalton project into a Lisp codebase. The entire interface is contained in this file, in case you find it helpful.
The example I think only works because of type defaulting:
This is correct.
Should there be a dynamic-scoped type context set on (lisp) entry so the type isn't forgotten?
The inner macro expansion of coalton
is a separate call to the compiler that won't share type information with the outer call. I think the inner call will be expanded after the outer coalton-toplevel
has finished compiling.
Alternatively: Some way to turn the typeclass dictionary into a value, pass it to (lisp), and call a typeclass-based method using it. Both approaches could make sense to implement, even together.
We could expose a primitive for doing this.
I'm not sure if it would work for your use case, but it's often possible to have the compiler generate specialized implementations of generic methods automatically. These can then safely be passed to lisp code. See the implementation of sort and sortBy for vectors which combines cl:sort
with the Ord
type class.
Produces the error:
This might be expected looking at the Design Document:
And using a nested lisp form does let the
Integer
case compile:But with parametric types or typeclasses, there's no way to refer to the original type. This was the original reason I used a nested Coalton: So that Lisp code could dispatch to the appropriate implementation of a class.
The example I think only works because of type defaulting:
If a non-special class is used, the trick doesn't work:
fails with error:
The
:a
in the nested lisp form does not refer to the top-levelbar
signature's:a
. It's a freshly-generated type. The style warning is complaining the typeclass dictionary isn't used, because it's forgotten. Then because the top-level x is forgotten, there's no way to get its type or to unify a fresh type with it. So the inner coalton fails to codegen because it can't access the unused dictionary. So it seems like this function can't be written.Should there be a dynamic-scoped type context set on (lisp) entry so the type isn't forgotten?