Elm defines the following special type variables that have a particular meaning to the compiler:
comparable: Comprised of
String and tuples thereof. This allows the use of the
Example: You could define a function to find the smallest and largest elements in a list (
extent). You think what type signature to write. On one hand, you could write
extentInt : List Int -> Maybe (Int, Int) and
extentChar : List Char -> Maybe (Char, Char) and another for
String. The implementation of these would be the same:
extentInt list = let helper x (minimum, maximum) = ((min minimum x), (max maximum x)) in case list of  -> Nothing x :: xs -> Just <| List.foldr helper (x, x) xs
You might be tempted to simply write
extent : List a -> Maybe (a, a), but the compiler will not let you do this, because the functions
max are not defined for these types (NB: these are just simple wrappers around the
< operator mentioned above). You can solve this by defining
extent : List comparable -> Maybe (comparable, comparable). This allows your solution to be polymorphic, which just means that it will work for more than one type.
number: Comprised of
Float. Allows the use of arithmetic operators except division. You can then define for example
sum : List number -> number and have it work for both ints and floats.
appendable: Comprised of
List. Allows the use of the
compappend: This sometimes appears, but is an implementation detail of the compiler. Currently this can't be used in your own programs, but is sometimes mentioned.
Note that in a type annotation like this:
number -> number -> number these all refer to the same type, so passing in
Int -> Float -> Int would be a type error. You can solve this by adding a suffix to the type variable name:
number -> number' -> number'' would then compile fine.
There is no official name for these, they are sometimes called:
This is because they work like Haskell's Type Classes, but without the ability for the user to define these.