pub enum Type {
Literal(TypeLiteral),
Variable(TypeVariable),
Fun {
param_tpe: Box<Type>,
return_tpe: Box<Type>,
},
Tuple(Tuple<Type>),
Unit,
Adt(QualName, Vec<Type>),
Record(BTreeMap<Name, Type>),
}Variants§
Literal(TypeLiteral)
Variable(TypeVariable)
Fun
Tuple(Tuple<Type>)
Unit
The unit type, (), whose one
value is also written ().
A variant of its own, the way Type::Tuple is, rather than a Type::Adt
known by the qualified name of a declaration the way Bool is: nothing
declares (), it is a form of type expression and never a name, so there is
no declaration to name and no same-spelled type it has to be told apart from.
See canonical::Type::Unit.
Adt(QualName, Vec<Type>)
A named algebraic data type, e.g. Maybe Int declared in Maybe →
Adt(Maybe.Maybe, [Literal(Int)]).
The name is the declaring package’s and module’s, in full, because that is the
identity of the type: Widget.Size and Gadget.Size are two types and a value
of one is never a value of the other, and so are the Size.Size of two
packages. The unifier’s equality on this name is the only thing keeping them
apart, so narrowing it to the spelling — which is what the typer used to carry —
made every same-named declaration one type (BUG-35).
Display still writes the unqualified half, since that is
how a module’s source spells its own types.
Record(BTreeMap<Name, Type>)
A record type: each label, and the type of the field it names.
A map, for the reason canonical::Type::Record is one: a record type is a set of
fields, so { x : Int, y : Int } and { y : Int, x : Int } are one value here and
nothing downstream can tell the two spellings apart. The map is ordered by label,
which is the order Display writes the fields in.
§How two record types unify
They unify when they carry the same set of labels and each label’s two field
types unify; see unify_one_constraint. There is no row variable, and nothing
ever adds a field to a record type: records are
closed, so a variable only ever
stands for a whole type, a record type included. Two record types with different
label sets are a plain ErrorKind::UnificationFailed, and its diagnostic names
the labels each side has that the other lacks (see Error’s notes).
Every walk over a type — substitution, the occurs check, instantiation, the zonk, and both renderings — goes into each field’s type as it goes into a tuple’s elements, and nothing else about a record is special to any of them.
What does not produce one is a use of a record: an access, an update or an
accessor says of a type only that it has some label, and is read against a record
type something else supplied — see FieldConstraint.
Trait Implementations§
Source§impl Display for Type
Writes a type the way the source would spell it, so diagnostics can quote it.
impl Display for Type
Writes a type the way the source would spell it, so diagnostics can quote it.
This is deliberately not Debug: Debug prints the typer’s own vocabulary
(Lit(Int), Var(#3)), which is what you want at a breakpoint and never what
you want in a message the user reads. Inference variables have no source syntax
at all, so they are written t3 — Elm’s convention for an unsolved variable.
impl Eq for Type
impl StructuralPartialEq for Type
Auto Trait Implementations§
impl Freeze for Type
impl RefUnwindSafe for Type
impl Send for Type
impl Sync for Type
impl Unpin for Type
impl UnsafeUnpin for Type
impl UnwindSafe for Type
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> CloneToUninit for Twhere
T: Clone,
impl<T> CloneToUninit for Twhere
T: Clone,
§impl<Q, K> Equivalent<K> for Q
impl<Q, K> Equivalent<K> for Q
§fn equivalent(&self, key: &K) -> bool
fn equivalent(&self, key: &K) -> bool
§impl<Q, K> Equivalent<K> for Q
impl<Q, K> Equivalent<K> for Q
§fn equivalent(&self, key: &K) -> bool
fn equivalent(&self, key: &K) -> bool
key and return true if they are equal.