我有一个接口和一个看起来像这样的值类:
public interface ITest<T1> {
<T2> T1 test(OtherClass<T2> client);
}
基本上,它表示子类型必须实现返回T1的方法test
,无论实现子类型是什么。
OtherClass:
public class OtherClass<T> {
public T contents;
}
但是,当我想编写一个实现test
的子类型并且只返回它获得的客户端实例时,我会遇到编译错误。我想要的是统一T1
和T2
:
public class Test<T1> implements ITest<T1> {
@Override
public <T1> T1 test(OtherClass<T1> client) { // compile error
return client.contents;
}
}
有没有办法让这个课上班?
答案 0 :(得分:1)
我不认为这是允许的,因为您现在将T2
限制为班级T1
中的Test<T1>
。
您可以按如下方式解决此问题:
public interface ITest<T1, T2> {
T1 test(OtherClass<T2> client);
}
public class OtherClass<T> {
public T contents;
}
public class Test<T1> implements ITest<T1, T1> {
@Override
public T1 test(OtherClass<T1> client) {
return client.contents;
}
}
答案 1 :(得分:1)
<T1>
基本上告诉任何一个班级&#34;你选择T1将是什么类型!&#34;。这意味着在这种情况下<T1>
和OtherClass<T1>
引用相同的类型,而返回类型T1
引用类T1
。如果重命名,则会看到错误:
@Override
public <OtherClassType> T1 test(OtherClass<OtherClassType> client) {
return client.contents; //you can't do that without casting OtherClassType to T1
}
如果你不能编辑ITest
接口,那么编译它的唯一方法是通过强制转换,但你需要确保在执行之前可以实际执行(因为OtherClass可以返回任何类型,而不是必然是T1的子类。
编辑:编译器不允许这样做的确切原因是因为您实际上限制test
方法只接受某些类型,而它覆盖的方法允许任何类型。