Is there a way to make polymorphic references constants in signatures?
This code compiles, but is not what I need:
signature NAME = sig
type 'a name
val empty : 'a name
end
structure Name :> NAME = struct
datatype 'a name = Nil | Val of 'a
val empty = Nil
end
Adding the required references:
signature NAME = sig
type 'a name
val empty : 'a name ref
end
structure Name :> NAME = struct
datatype 'a name = Nil | Val of 'a
val empty = ref Nil
end
Produces the following error:
error: Structure does not match signature.
Signature: val empty: 'a name ref
Structure: val empty: 'a name ref
Reason: Can't match 'a to 'a (Type variable is free in surrounding scope)
Found near struct datatype 'a name = Nil | Val of 'a val empty = ref Nil end
This doesn't actually have to do with signatures; you'd get the same sort of issue if you wrote (at top-level):
val emptyListRef = ref nil
val emptyIntList = (! emptyListRef) : int list
val emptyStringList = (! emptyListRef) : string list
The issue is that emptyListRef — or in your case empty — can't be polymorphic. (Your compiler claims that empty has type 'a name ref, but what it really means is that empty will have some type of the form ?? name ref, and it hasn't yet figured out what ?? will be.)
This restriction makes sense when you consider that if empty were polymorphic, then you'd be able to write things like:
val () = empty := Val 3
val Val (x : string) = !empty
where you set empty to hold an int Name and then read from it as if it held a string Name. There's no way the convince the compiler to trust that you won't do that.
The general rule is that value bindings are only allowed to be polymorphic if the right-hand side takes one of a few simple forms, like combinations of constructors (other than ref!) and constants and fn-expressions, that are known to be safe (in that they can't enable the above-described misbehavior). This rule is called the value restriction; you can Google that term to get much more information.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With