Я создаю новый интерфейс в Java, и я хочу создать метод, который возвращает тот же тип класса, который реализует интерфейс.
Пример:
public interface ModelInterface {
public (TypeOfClass) getAll();
}
public class Object1 implements ModelInterface {
public Object1 getAll(){
}
}
public class Object2 implements ModelInterface {
public Object2 getAll(){
}
}
Как я могу это сделать?
Java имеет свойство ковариантных типов возврата. Это означает, что подкласс может определять подкласс возвращаемого типа метода при переопределении/реализации метода. Это так просто, как
public interface ModelInterface {
public ModelInterface getAll();
}
public class Object1 implements ModelInterface {
public Object1 getAll(){
// implement here
}
}
public class Object2 implements ModelInterface {
public Object2 getAll(){
// implement here
}
}
В этом учебнике дается объяснение ковариантным типам возврата.
Предположим, что у вас есть иерархия классов, в которой ImaginaryNumber является подклассом java.lang.Number, который, в свою очередь, является подклассом Object.
Теперь предположим, что у вас есть метод, объявленный для возврата Number:
public Number returnANumber() { ... }
Метод returnANumber может возвращать ImaginaryNumber, но не объект. ImaginaryNumber - это число, потому что это подкласс Number. Тем не менее, объект не обязательно является числом - это может быть строка или другой тип.
Вы можете переопределить метод и определить его для возврата подкласса исходного метода, например:
public ImaginaryNumber returnANumber() { ... }
Этот метод, называемый ковариантным типом возврата, означает, что возвращаемый тип может меняться в том же направлении, что и подкласс.
Примечание. Вы также можете использовать имена интерфейсов в качестве типов возврата. В этом случае возвращаемый объект должен реализовать указанный интерфейс.
ModelInterface getAll()
, а не уточненный тип. Таким образом, за исключением небольшого уточнения в способе , за исключением (как возвращаемый объект будет вентиляционным молча в любом случае) , это не особенно полезны в контексте.
Вы можете аппроксимировать такой тип возврата в интерфейсе, используя дженерики
interface Foo<T extends Foo<T>> {
T method();
}
Таким образом, вы помните компилятору, что общий тип должен быть совместим с типом, который реализует Foo
Этот тип может быть Foo
сам или любым другим типом, который реализует этот интерфейс. Когда используешь:
class Bar implements Foo<Bar>
все ваши методы, однако, вынуждены возвращать Foo
как ожидалось.
Object
и typecast результат в зависимости от класса, который реализует интерфейс ...