In Haskell the trivial type is written as ()
and has kind ∗. The list type is written as []
and has kind ∗→∗, which means that it is sort of a 'metafunction' from type to type. Applying []
(kind ∗→∗) to Int
(kind ∗) gives [] Int
i.e. [Int]
(kind ∗). The function type is written as (->)
and has kind ∗→∗→∗ i.e. ∗→(∗→∗) which means it's a sort of metafunction from type to a function from type to type. Applying (->)
(kind ∗→∗→∗) to Int
(kind ∗) gives (->) Int
(kind ∗→∗), and applying that to Float
(kind ∗) gives (->) Int Float
i.e. Int -> Float
(kind ∗).
In Alvin the trivial type is written as Trivial
. The list type is written as List
. It is a template, taking a type and 'returning' a type. Applying List
to Int
gives List::value<Int>
. The function type is written as Function
. (->) Int
is written as Function::value<Int>
and Int -> Float
is written as Function::value<Int>::value<Float>
.
Haskell:
1
is a value of typeInt
.1.0
is a value of typeFloat
.[]
is a value of type[]
.1:[]
is a value of type[] Int
i.e.[Int]
.1:2:3:[]
is a value of type[] Int
i.e.[Int]
.- After
weird x = [x, 1]
,weird
is a value of type(->) Int ([] Int)
i.e.Int -> [Int]
.
Alvin:
Int::value<1>
is a value of typeInt
.Float::value<1.0>
is a value of typeFloat
.EmptyList::value<T>
is a value of typeList::value<T>
.Cons::value<Int::value<1>>::value<EmptyList<Int>>
is a value of typeList::value<Int>
.Cons::value<Int::value<1>>::value<Cons::value<Int::value<2>>::value<Cons::value<Int::value<3>::value<EmptyList::value<Int>>>>
is a value of typeList::value<Int>
.- After
class Weird { template <typename T> using value = Cons::of<T>::with<Cons::of<Int::value<1>>::with<EmptyList::value<Int>>>; };
,Weird
is a value of typeFunction::from<Int>::to<List::of<Int>>
.
It's a little more verbose than Haskell.