Java泛型 - 类<! - ? - >构造函数参数问题

时间:2013-06-06 13:05:49

标签: java hibernate generics search hibernate-search

我已经使用Java很长一段时间了,但有些事情对我来说仍然不太清楚,特别是涉及到泛型......

事情就是这样:我有一个我正在使用的Search类(see here for details),它的构造如下:

public Search(Class<?> searchClass) {...}

此外,我有一个参数化的通用包装器,如下所示:

public class HibernateSearch<E> extends Search implements Serializable {
    public HibernateSearch(Class<E> entityClass) {
        super(entityClass);
    }
    // ... omitted for brevity
}

现在,我需要的是:我想创建一个参数化类,它包含这个类作为它的字段,例如。

public class BaseSelectorComposer<T> extends SelectorComposer<Window> {

    private HibernateSearch<T> searchObject;
    ...
    @Override
    public void doAfterCompose(Window comp) throws Exception {
        super.doAfterCompose(comp);
        this.searchObject =
             new HibernateSearchObject<T>( now what...??? );
        ...
    }
    ...
}

我认为我所面对的问题在给定的例子中是显而易见的 有人可以建议在这里可以做些什么,或者其他一些选择吗?

2 个答案:

答案 0 :(得分:5)

最简单的方法是将责任转嫁给实际实例化并使用BaseSelectorComposer实例的人,即:

public class BaseSelectorComposer<T> extends SelectorComposer<Window> {

    private HibernateSearch<T> searchObject;
    private final Class<T> theType;

    public BaseSelectorComposer(Class<T> token) {
        theType = token;
    }

    ...
    @Override
    public void doAfterCompose(Window comp) throws Exception {
        super.doAfterCompose(comp);
        this.searchObject = new HibernateSearchObject<T>(theType);
        ...
    }
    ...
}

如果你的BaseSelectorComposer是一个抽象的子类,它只被用作

class IntSelectorComposer extends BaseSelectorComposer<Integer> {
    ...
}

即,作为类的基类,“绑定”类型参数,有obtain the type information via reflection的方法(虽然这非常难看,因为这在API恕我直言中并没有得到很好的支持)。 / p>

答案 1 :(得分:1)

通常,这是一种难以解决的方案。来自.NET背景,我个人发现很少有我可以解决的问题,因为Java不支持静态泛型类型解析(例如在.NET中你可以使用typeof(T))。

为了解决这个问题,我建议您找到一种方法来从外部获取类,或者该类的实例。可能的解决方案是通过以下方式之一更改doAfterCompose方法:

@Override
public void doAfterCompose(Window comp, Class<?> entityClass) throws Exception {
    super.doAfterCompose(comp);
    this.searchObject =
         new HibernateSearchObject<T>(entityClass);
    ...
}

-OR -

@Override
public void doAfterCompose(Window comp, SomeEntity entity) throws Exception {
    super.doAfterCompose(comp);
    this.searchObject =
         new HibernateSearchObject<T>(entity.getClass());
    ...
}

如果您无法修改方法签名(我看到它是覆盖),请尝试使用将保留所需BaseSelectorComposer<T>实例的类Class<?>的成员。

public class BaseSelectorComposer<T> extends SelectorComposer<Window> {
    private Class<?> entityClass;

    public BaseSelectorComposer<T>(Class<?> entityClasss) {
        this.entityClass = entityClass;
    }

   ....
    @Override
    public void doAfterCompose(Window comp) throws Exception {
        super.doAfterCompose(comp);
        this.searchObject =
            new HibernateSearchObject<T>(this.entityClass);
       ...
    }
}