Java-有界泛型作为有界泛型方法的输入
给定一个泛型类型Java-有界泛型作为有界泛型方法的输入,java,generics,bounded-wildcard,Java,Generics,Bounded Wildcard,给定一个泛型类型Result,并使用以下部分实现 public class Result<T> { /* fields, ctor, etc... */ public Result<T> mergeWith(Result<? extends T> other) { /* fiddle with this and other (acting as producer) and return */ } /* ot
Result
,并使用以下部分实现
public class Result<T> {
/* fields, ctor, etc... */
public Result<T> mergeWith(Result<? extends T> other) {
/* fiddle with this and other (acting as producer) and return */
}
/* other methods */
}
上述示例失败,并显示给定的类型不匹配错误消息
我已经尝试更改.mergeWith的签名,以接受更窄的
结果,而不是结果根据结果的合并声明,当且仅当T是s的子类型时,您可以将结果与结果合并
在聚合方法中,左的类型参数是节点的某个未知子类,右的类型参数也是节点的某个未知子类。不能保证right的type参数是left的子类
如果您尝试以下方法:
public <S extends Node, T extends S> Result<? extends Node> aggregate(Result<S> left, Result<T> right) {
Result<? extends Node> temp = left.mergeWith(right);
/** do stuff*/
return temp;
}
公共结果问题来自于相互独立的?
捕获。不要在类定义中使用?
捕获。使用泛型类型标识符:
public class SomeVisitor<T extends Node> implements Visitor<Result<T>> {
public Result<FileNode> visitFile() { }
/* ... */
protected Result<T> aggregate(Result<T> left, Result<T> right) {
Result<T> tempResult = left.mergeWith(right);
}
}
public类SomeVisitor实现Visitor{
公共结果visitFile(){}
/* ... */
受保护的结果聚合(结果左、结果右){
结果tempResult=left.mergeWith(右);
}
}
这是一种非常巧妙(但非常Java-y)的解决方法。不幸的是,我正在实现的接口将聚合描述为T聚合(T左,T右)代码>也许我应该用以下信息来补充这个问题:)对不起!不确定这是否可以不铸造。。。然而,看起来你只需要投一次。tempLeft.mergeWith(右)应该有效。实现访问者
不会编译,因为泛型类型标识符的边界必须在实现类上定义,而不是在interface.oops上定义。我会解决的。我打算将类声明为SomeVisitor
您能显示Visitor.visitFile()
签名吗?此外,它还将有助于展示如何实际使用SomeVisitor
。@shmosel done。希望能有帮助。
FileContext fileCtx = someOtherService.acquireFileContext();
SomeVisitor visitor = new SomeVisitor();
Result<FileNode> fileNodeResult = visitor.visitFile(fileCtx);
// process the result
@SuppressWarnings("unchecked")
Result<Node> tempLeft = (Result<Node>) left;
@SuppressWarnings("unchecked")
Result<Node> tempRight = (Result<Node>) right;
Result<Node> tempResult = tempLeft.mergeWith(tempRight);
public <S extends Node, T extends S> Result<? extends Node> aggregate(Result<S> left, Result<T> right) {
Result<? extends Node> temp = left.mergeWith(right);
/** do stuff*/
return temp;
}
public class SomeVisitor<T extends Node> implements Visitor<Result<T>> {
public Result<FileNode> visitFile() { }
/* ... */
protected Result<T> aggregate(Result<T> left, Result<T> right) {
Result<T> tempResult = left.mergeWith(right);
}
}