Hi,
Is there any way of creating an alias for an empty list of a particular type, something like:
type EmptyA = List[A]()
?
I’ve tried it by doing:
object EmptyA extends List[A]()
but list is final.
Hi,
Is there any way of creating an alias for an empty list of a particular type, something like:
type EmptyA = List[A]()
?
I’ve tried it by doing:
object EmptyA extends List[A]()
but list is final.
I’m not sure what you’re hoping to achieve. An object representing an empty list already exists: Nil
.
You can alias it if you want:
val empty = Nil
// or "specialized" to type A:
val emptyA: List[A] = Nil
Note that Nil
is a subtype of List[Nothing]
. List
is covariant and Nothing
is a subtype of every other type. So List[Nothing]
is compatible with any other type. 42 :: Nil
is a List[Int]
. "foo" :: Nil
is a List[String]
. "foo" :: 42 :: Nil
is a List[Any]
.
If you want a type alias instead I’d go with type EmptyList = List[Nothing]
. You cannot have a type alias representing an empty List[A]
. You can’t see in the type alone whether a list is empty or not. Except for List[Nothing]
, because there is no value of type Nothing
.
Would the call to List.empty[A]
work fine for you?
Thanks for the comments. I was thinking about say modelling polynomials where the empty list is Zero - and whether it is possible to rename the empty list to Zero. However, I’m not sure if this could cause confusion between the concept and its representation.
It sounds like you want to distinguish between the empty list and non-empty lists on the type level.
There are three types you want to exist for that, the type of empty lists, the type of non-empty lists, and the type of lists that could be empty or could be non-empty.
In the standard library, the value Nil
is the empty list, and its singleton type, Nil.type
could be used for the empty list. List[+A]
is the type of lists that could be empty or could be non-empty. The type of non-empty lists is ::
.
Using them for something sensible tends to be difficult – List
doesn’t abstract over its length, so you don’t know whether the tail of some ::
is a ::
or a Nil.type
. In addition, if you know something to be Nil.type
at compile time, you know its value is going to be Nil
, and you can usually deal with this by not abstracting over it at all, but special-casing the Nil
case on the term level.
It’s more common to have a use for the opposite: the non-empty list. It’s also not easy working with that in the stdlib, since ::
is really seen as a constructor of List
, and all operations that could return ::
return List
instead. It’s worth noting that the cats
library provides a NonEmptyList
class.
Another library that may be of interest is shapeless, which does have the mechanisms to abstract over list arity.
If polynomials are central to your project, they deserve to be a type on their own. Consider wrapping your Lists into a case class or a value class.