Ale*_*nov 3 java generics bounded-wildcard
假设我有一个界面
interface Foo<T> {
void foo(T x);
T bar()
}
Run Code Online (Sandbox Code Playgroud)
以及具有未知参数的此类对象:Foo<?> baz.然后我可以打电话baz.foo(baz.bar()).
但是,现在我需要将值baz.bar()放入集合中,baz.foo()稍后再调用它.就像是
List<???> list; // can I tell the compiler this is the same type as baz's wildcard?
list.add(baz.bar());
...
baz.foo(list.get(1));
Run Code Online (Sandbox Code Playgroud)
这也不起作用:
List<Object> list;
list.add(baz.bar());
...
baz.foo((???) list.get(1)); // I can't write down the type I need to cast to
Run Code Online (Sandbox Code Playgroud)
有没有办法做到这一点?
编辑:以上是从我的实际情况过分简化.说我们有
class Bar {
private final Foo<?> foo;
private List<???> list; // the type argument can be selected freely
Bar(Baz baz) {
foo = baz.getFoo(); // returns Foo<?>, can't be changed
}
void putBar() {
list.add(foo.bar());
}
void callFoo() {
foo.foo(list.get(0));
}
}
Run Code Online (Sandbox Code Playgroud)
您可以将逻辑包装在这样的泛型方法中:
public <T> void myMethod(Foo<T> baz) {
List<T> list; // initialise it...
list.add(baz.bar());
// ...
baz.foo(list.get(1));
}
Run Code Online (Sandbox Code Playgroud)
这是我所知道的唯一方式,实现你想要的,而不需要不安全的铸造.
OP编辑后:
正如其他人所提到的,外部类Bar需要知道常见的泛型类型T.此外,随着您不能够改变的签名的约束Baz.getFoo(),我想你必须投不安全Foo<?>对Foo<T>在构造函数Bar<T>:
class Bar<T> {
private final Foo<T> foo;
private List<T> list;
Bar(Baz baz) {
// Since baz cannot be changed, you will have to
// unsafe cast Foo<?> to Foo<T> here.
foo = (Foo<T>) baz.getFoo();
}
void putBar() {
list.add(foo.bar());
}
void callFoo() {
foo.foo(list.get(0));
}
}
Run Code Online (Sandbox Code Playgroud)
或者(因为Foo,Bar,Baz不是理解你的真实用例的好方法),你仍然可以避免这样的泛化Bar:
class Bar {
private final Foo<Object> foo;
private List<Object> list;
Bar(Baz baz) {
// Since baz cannot be changed, you will have to
// unsafe cast Foo<?> to Foo<Object> here.
foo = (Foo<Object>) baz.getFoo();
}
void putBar() {
list.add(foo.bar());
}
void callFoo() {
foo.foo(list.get(0));
}
}
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
269 次 |
| 最近记录: |