有人已经指出,既无解决办法,也无ice事。 这是我最后做的。 这只是为我的特殊案例而努力的,但如果你遇到类似问题,你可以把它看作是一种灵感。 (这也是我为什么要处理这个问题的原因)
首先,有这一类(仅指相关接口):
class Pipe<Input, Output> {
boolean hasNext();
Input getNext();
void setNext(Output o);
}
接口实际上为:
interface Processor<Input, Output> {
process(Pipe<Input, Output> p);
}
和<代码>Bar等同工作
class JustCopyIt<Input, Output> implements Processor<Input, Output> {
process(Pipe<Input, Output> p) {
while (p.hasNext()) p.setNext(p.getNext());
}
}
The easiest way would be to cast the values like this: p.setNext((Output) p.getNext())
.
But this is bad as it would allow to create an instance of JustCopyIt<Integer, String>
. Calling this object would mysteriously fail at some point, but not at the point where the actual error is made.
Doing class JustCopyIt<Type> Implements 加工商和提炼;Type, 类型和特有;
也不会在这里工作,因为当时我无法处理<代码>Pipe<String, Object>。
So what I finally did was to change the interface to this:
interface Processor<Input, Output> {
process(Pipe<? extends Input, ? super Output> p);
}
这样,JustCopyIt<List>
就能够处理Pipe<ArrayList, Collection>
。
虽然这一技术上似乎是唯一有效的解决办法,但这一解决办法仍然不正确,因为它1)只针对这一特殊案例开展工作,2)要求我改变接口(并非总是可能的),3)使其他处理器的代码变得模糊不清。
Edit:
Reading Keiths answer again inspired me for another solution:
public abstract class Bar<A, B> implements Foo<A, B> {
public static <B, A extends B> Bar<A, B> newInstance() {
return new BarImpl<B, A>();
}
private static class BarImpl<B, A extends B> extends Bar<A, B> {
// code goes here
}
}
// clean code without visible reversed parameters
Bar<Integer, Object> bar1 = Bar.newInstance();
Bar<Object, Integer> bar2 = Bar.newInstance(); // <- compile error