简体   繁体   中英

Error using an Interface as a return type [Java]

I've these two Java interfaces:

the first one is:

public abstract interface A {

}

and the second one is:

public abstract interface B {
    public abstract Set<A> methodName();
}

Then, I've implemented these two interfaces as:

public class AImpl implements A {

}

and:

public class BImpl implements B {
    private Set<AImpl> p;  

    public Set<A> methodName() {
        return this.p;
    }
}

I don't understand why I obtain the following error about the implementation of methodName():

Type mismatch: cannot convert from Set<AImpl> to Set<A>

Thank you very much.

Set<AImpl> is not exactly the same what Set<A> , you cannot convert it. You can:

  • declare p as Set<A>
  • declare p as Set<? extends A> Set<? extends A>
  • return Set<AImpl> in methodName()

More details: if AImpl implements/extends A then List<AImpl> does not implement/extend List<A> . List<? extends A> List<? extends A> means that this is the list of something that extends/implements A.

Look at Wildcards and subtyping in Java Tutorial

To add something in Patryk Dobrowolski's answer

Here problem is Set<Car> is different than Set<Vehicle> note here that Car is a Vehicle but you can't add Scooter which is also a Vehicle to Set<Car> but Set<Vehicle> may have Car , Bike , Scooter etc. but you can't add other vehicles in Set<Car> .

Set<AImpl> to Set<A> , your Set<AImpl> is of type AImpl not A

public class BImpl implements B {
    private Set<A> p;  

    public Set<A> methodName() {
        return this.p;
    }
}

Change Set<AImpl> p to Set<A> p and return type of method to Set<AImpl> .

Set<A> is different from Set<AImpl> . Consider what would happen if this was possible:

class AImpl implements A {...}
class AImpl2 implements A {...}

Set<AImpl> aimpls = new Set<AImpl>();
Set<A> foo = aimpls;
foo.add(new AImpl2());

AImpl value = aimpls.iterator().next(); //ClassCastException - it's actually an AImpl2

If you're only going to be reading from p , then it would be safe to assign a Set<AImpl> to it, but in that case it should be:

Set<? extends A> p;
public Set<? extends A> methodName() {
    return this.p;
}

First lets discuss why you are getting this error

In the class BImpl you have created a variable of type Aimpl . In the method you have return type of interface class A .

In the method you are trying to return a value of type Aimpl . However the compiler expects a return value of type A . That is why you are getting this error

Now how to avoid it

Change the return type of your method to Set<Aimpl> or declare p as suggested by Patryk

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM