Версия 1
public interface Outer<T>{
public interface Inner<T>{
T get();
void set(T t);
}
}
Несмотря на одинаковый синтаксис универсального типа, эти два типа полностью независимы.
Версия 2
public interface Outer<T>{
public interface Inner<V extends T>{
V get();
void set(V t);
}
}
Получил ошибку: "Невозможно сделать статическую ссылку на нестатический тип T"
Версия 3
public interface Outer<T>{
public interface Inner{
<T> T get();
<T> void set(T m);
}
}
Не уверен, что это то, что я хочу, но кажется, что все в порядке (в eclipse нет ошибок), поэтому я пытаюсь реализовать это:
public Test implements interface Outer.Inner {
//no problem in these two
<T> T get(){..};
<T> void set(T m){...};
//Errors come up here:
Map<String,T> map;
public Test(Map<String,T> map){
this.map=map
}
}
Появляется ошибка: «T не может быть разрешен к типу» в обоих
- декларация
Map<String,T> map
- аргумент конструктора
public Test(Map<String,T> map){}
Итак, как я могу решить эту проблему?
4 ответа
Источник вашей проблемы в этом; Внутренний интерфейс является статическим, поэтому он не связан с каким-либо экземпляром внешнего интерфейса. Поэтому вы не можете использовать общий тип внешнего интерфейса для внутреннего интерфейса.
Согласно JLS;
9.5 Объявления типов членов
Интерфейсы могут содержать тип члена декларации (§8.5). Тип члена объявление в интерфейсе неявно статический и общедоступный
Что вам следует сделать, так это, возможно, иметь Inner extends Outer, если тип должен быть обязательно применен, но, конечно, вам придется реализовать методы как Inner, так и Outer. Я не уверен, что ты этого хочешь.
interface Outer<T> {
interface Inner<T> extends Outer<T> {
T myMethod(T t);
}
}
На самом деле нет другого способа обеспечить то, что вы хотите. Причина в том, что интерфейс всегда статичен. Кроме того, вы действительно не хотите/не нуждаетесь в таком поведении: интерфейс уже достаточно гибок для вас. Просто узнайте, где вы можете контролировать это, и мир будет вашим!
Ошибка в реализации - вы забыли добавить универсальный тип, это должно помочь:
public class Test<T> implements interface Outer<T>.Inner {
T get(){..};
void set(T m){...};
//Errors come up here:
Map<String,T> map;
public Test(Map<String,T> map){
this.map=map
}
}
Во-первых, сделать это никак нельзя, так как внешний интерфейс — не что иное, как «пространство имен» для внутреннего интерфейса. Им действительно больше нечего делать друг с другом.
Возникает вопрос: зачем вам такой контроль над вещами? Если в классе, реализующем интерфейс, будет решено, что использование одного и того же типа имеет смысл, то так и будет для этого класса. Но другая реализация может и должна иметь право выбирать иное. Это особенно верно, поскольку классы, реализующие Outer, и те, которые реализуют Inner, не ограничены вложением друг в друга.
Похожие вопросы
Новые вопросы
java
Java — это высокоуровневый объектно-ориентированный язык программирования. Используйте этот тег, если у вас возникли проблемы с использованием или пониманием самого языка. Этот тег часто используется вместе с другими тегами для библиотек и/или фреймворков, используемых разработчиками Java.