无法从Guava解析通用参数TypeToken

我正在开发一个用于为Selenium测试框架构建通用菜单的框架,并且我一直在使用Guava

TypeToken来解析通用参数的类型,但是现在我遇到了一个问题,其中类型令牌无法解析参数:

我有一个生成菜单选项的构建器abstract基础class

public abstract class AbstractMenuOptionBuilder<O extends IClickable>  {

protected final TypeToken<AbstractMenuOptionBuilder<O>> typeToken = new

TypeToken<AbstractMenuOptionBuilder<O>>(getClass()) { };

public abstract O create();

}

这是class建造者的具体做法:

public class MenuOptionBuilder<O extends IClickable> extends AbstractMenuOptionBuilder<O> {

public O create() {

TypeToken<?> genericOptionParam = typeToken.resolveType(AbstractMenuOptionBuilder.class.getTypeParameters()[0]);

Class<O> optionClass;

try {

optionClass = (Class<O>) Class.forName(genericOptionParam.getType().getTypeName());

<.... snip ....>

} catch(ClassNotFoundException e) {

log.catching(e);

return null;

}

}

}

我有一个菜单abstract基础class,它具有一种返回菜单选项列表的方法:

public abstract class AbstractMenu<O extends IClickable> {

public final List<O> getOptions() {

//This is where my plan doesn't work. The runtime type is given by

//a concrete menu class which extends AbstractMenu, but that runtime

//type doesn't seem to pass through to the abstract base class for the builder.

MenuOptionBuilder<O> builder = new MenuOptionBuilder<O>(new MenuOptionBean()){};

<.... snip ....>

}

}

我有一个具体的菜单classextends它:

   //The runtime type of 'Link' is not known by the type token that is supposed to

//resolve it in the abstract builder base class.

public SimpleMenu extends AbstractMenu<Link> {

<.... snip ....>

}

我曾期望genericOptionParamin

中的变量MenuOptionBuilder可以解析为通用类型参数的名称,而不是其运行时类型为Link,但不能解析为。如果我像这样创建一个额外的基础,则通用参数可以正确解析:O``Link``class

public abstract class AbstractSimpleLinkedMenu extends AbstractMenu<Link> {

public final List<Link> getOptions() {

MenuOptionBuilder<Link> builder = new MenuOptionBuilder<Link>(new MenuOptionBean()){};

<.... snip ....>

}

}

我不希望不必添加其他基础类,例如AbstractSimpleLinkedMenu,那么这里是否有我错过或做错的事情?我以为抽象生成器的匿名内部类会知道运行时类型,如果使用通用参数声明该生成器,则不会。运行时类型由具体菜单class,指定SimpleMenu,但似乎无法过滤到abstract菜单选项的构建器类。

回答:

这就是TypeToken“ hack”的

工作方式。它使用Class#getGenericSuperclass()(或getGenericSuperInterface)。它的javadoc状态

如果超类是参数化类型,则Type返回的对象必须准确反映

在这种情况下,也就是O,在这里

public abstract class AbstractMenuOptionBuilder<O extends IClickable>

您将获得源代码中的硬编码内容。如果您将代码硬编码Link为类型参数,请按照此处的操作

MenuOptionBuilder<Link> builder = 

new MenuOptionBuilder<Link>(new MenuOptionBean()) {};

然后你会得到Link

在这种情况下

MenuOptionBuilder<O> builder = 

new MenuOptionBuilder<O>(new MenuOptionBean()){};

您已经进行了硬编码O,这就是您将得到的。

以上是 无法从Guava解析通用参数TypeToken 的全部内容, 来源链接: utcz.com/qa/399235.html

回到顶部