From what I can tell, these 2 functions are equivalent:
def x(xx: X forSome { type X <: Int }): Unit = ()
def y[Y <: Int](yy: Y): Unit = ()
According to my observations, nowadays people mostly use second form (that uses []
), at the same time I sometimes see articles (mostly old ones, discussing existential types) that use the first one (forSome
).
What is the reason behind having 2 notations? Is there a pros\cons or things you can\can't do using one or another?
They are very similar indeed, and you are not alone in the confusion. The best article I've read about existential types gives you a good explanation is indeed here (as @DaunnC mentions) . There is actually also a third way to express the same in Abstract Types.
As reasons go, I would argue that some things are just syntactic sugar and others product of the language's evolution. Scala 2.14 is scheduled to address some of the redundancy and simplify the language. in particular: