I recently saw a discussion on slack about the type annotations for functions that can return any type. For example: myList : List a
or myMaybe : Maybe a
Of course myList
must be an empty list because how else could it be a list containing any type of value.
Of course myMaybe
must be Nothing
because if it was Just 7
, Just "hello"
or Just anything
it would not be able to have the type Maybe a
.
Now it has taken me ~6 months of using with elm to realise the truth of the above two statements despite how obvious they seem to me now I have clocked them. For a long time, I thought that ports are defined with a generic return type because they were in some way âmagicâ. Instead, commands related to a port will never give a message back to the update function.
The realisation came when I was trying out rust and found https://doc.rust-lang.org/nightly/book/second-edition/ch19-04-advanced-types.html#the-never-type-that-never-returns. In rust there is a special symbol for this ânever typeâ which is !
.
If elm used !
for these never types and I had found a port definition like port myPort : String -> Cmd !
I may have been very confused. However, I then would have googled âexclamation mark elmâ and been taken to the elm docs (or stack overflow) where I would have understood that !
means that no messages can be produced. My confusion would have lasted ~5 minutes instead of ~6 months.
Note: the ânever typeâ in rust is very different from the elm Never
type. The special symbol I am proposing would work exactly like generic return types do currently. For example empty : List a
-> empty : List !
and the value could be used in exactly the same way as it is now.
I am not necessarily advocating using !
here, other symbols such as _
would also be viable. Something completely different may also be good.
To summarise
list1 : a -> List a
and list2 : a -> List b
look very similar but are infact have completely different implications. It would be good if they also looked very different.
Edit: added note about elmâs Never
.