Sometimes in Scala I find that I get type mismatches related to path-dependent types, but I can easily reason that in fact the types coincide. Here's a simple example:
trait Foo { trait Bar }
object Main extends App {
val foo1 = new Foo { }
val foo2 = foo1
def turkle(x: foo1.Bar) {}
turkle(new foo2.Bar {})
}
which gives: "type mismatch; found : java.lang.Object with Main.foo2.Bar required: Main.foo1.Bar".
Now of course the paths Main.foo1.Bar
and Main.foo2.Bar
must coincide, since we wrote val foo2 = foo1
. We can verify this, by changing the last line to
turkle((new foo2.Bar {}).asInstanceOf[foo1.Bar])
which both compiles and runs without an exception.
Can Scala automatically perform reasoning like this? If so, how can I make this happen?
(And if not, are there any prospects for extending the type system in this direction?)
I'll note that sometimes Scala does appear to perform this sort of reasoning. Supposing I change trait Foo
to object Foo
:
object Foo { trait Bar }
object Main extends App {
val foo1 = Foo
val foo2 = foo1
def turkle(x: foo1.Bar) {}
turkle(new foo2.Bar {})
}
Now everything compiles fine: somehow Scala has worked out that both Main.foo1.Bar
and Main.foo2.Bar
are really the same as Foo.Bar
.