Scala prohibiting parameterization of a specific type
Is there a way to prohibit a parameterized type being parameterized by a specific type?
e.g. Suppose I want to create my own specialized List[T] type where I do not want List[Nothing] to be legal, i.e. cause a compile error.
I'm looking for a way to make the following error more easy to catch (yes, I understand this is not very functional or great Scala):
val x = ListBuffer()
x += 2
开发者_运维技巧x has type ListBuffer[Nothing].
This sort of works,
class C[A](x: A*)(implicit ev: A =:= A) { }
There will be a type error if A = Nothing
is inferred,
val c1 = new C[Int]() // Ok
val c2 = new C(1) // Ok, type `A = Int` inferred
val c3 = new C() // Type error, found (Nothing =:= Nothing) required: (A =:= A)
But it's still possible to explicitly set the type parameter A
to Nothing
,
val c4 = new C[Nothing]() // Ok
More generally, it's pretty tricky to ensure that two types are unequal in Scala. See previous questions here and here. One approach is to set up a situation where equal types would lead to ambiguous implicits.
You can define a type A >: Null if you specifically want to avoid Nothing, as Null is second from bottom and also covariant to all types (therefore its contravariance includes all types apart from Nothing).
Not sure how useful this is as its type bounds still includes Null.
精彩评论