Search code examples
javascalatypesexistential-typebounded-wildcard

Java Generic Type Converted to Scala does not accept super class itself


I'm writing a framework. The interfaces are written and compiled in Java code. The client uses Scala and those interfaces. Here is an example of the interface.

public interface Context {
   MyComponent<? extends File> getComponent();
}

Now my scala code uses the interface as follows.

val component = context.getComponent();
println(calculate(component));

def calculate( component: MyComponent[File] ): Unit = ???

Scala compiler is throwing errors at line 2 for println(calculate(component)). The error is: Type mismatched, expected: MyComponent[File], actual: MyComponent[_ <: File].


Solution

  • Java's wildcard type

    ? extends File
    

    corresponds to the existential type

    _ <: File
    

    in Scala. Try changing the signature

    def calculate(component: MyComponent[File]): Unit = ???
    

    to

    def calculate(component: MyComponent[_ <: File]): Unit = ???
    

    Also note that if MyComponent were a Scala-class that is under your control, then changing the invariant type parameter to covariant type parameter +F might also work, because then every MyComponent[F] forSome { type F <: File } would be a special case of MyComponent[File].