泛型 - 无法转换为 T,其中 T 是类型变量

Generics - cannot be converted to T where T is a type variable

我知道这个问题已经被问得很恶心了;我想我对错误有所了解,但仍然不明白为什么我(试图)违反擦除限制。我也认为我以正确的方式使用泛型,如果不正确,请随时告诉我。

我有一个 AbstractService class(用于我的 Neo4j OGM 和 Hibernate 实现),每个都扩展了一些 classes,其中包含一些反映各个 Entity 对象的方法。各个实体对象都扩展了 DomainEntity,并且都是 Hibernate ORM 和 Neo4j OGM 实体。

我有两段代码(一段使用 Hibernate,另一段使用 Neo4j OGM)。两个方法调用(对第 3 方库)具有(几乎)相同的签名,我的方法具有相同的签名,但我的 OGM 代码抛出上述编译时错误,而我的 Hibernate 代码则没有。

OGM

import org.neo4j.ogm.session.Session;
import org.neo4j.ogm.transaction.Transaction;

public abstract class AbstractService<T extends DomainEntity> implements Service<T> {

    private Session session;

    @Override
    public abstract Class<T> getEntityType();

    public abstract String getUniqueProperty();

    public abstract String getLabel();

    public T getEntity(String property) {
        String query = "MATCH (x:" + getLabel() + ") WHERE x." + getUniqueProperty() + " = \"" + property + "\" RETURN x";
        return session.queryForObject(getEntityType(), query, Collections.EMPTY_MAP);
    }
}

这是 queryForObject 方法调用的签名:

public < T > T queryForObject(Class< T > objectType, String cypher, Map< String,? > parameters)

我在 return session.queryForObject(...) 行收到以下编译时错误:

incompatible types: DomainEntity cannot be converted to T where T is a type-variable: T extends DomainEntity declared in class AbstractService

但是,如果我在 return 之前将响应投射到 T,它会起作用,但我不明白为什么。 queryForObject 方法 returns T,这是我正在尝试的 return,所以我不明白为什么它需要在 [= 之前​​转换为 T 52=]ing.

EDIT 我尝试将泛型类型添加到方法调用中:

return session.<T>queryForObject(getEntityType(), query, Collections.EMPTY_MAP);

这并没有改变任何东西。


休眠

import org.hibernate.Session;

public abstract class AbstractService<T extends DomainEntity> implements Service<T> {

    private Session session;

    public T getEntity(String property) {
        String query = "SELECT * FROM " + getLabel() + " WHERE " + getUniqueProperty() + " = \'" + property + "\'";
        return getSession().createNativeQuery(query, getEntityType()).getSingleResult();
    }

    @Override
    public abstract Class<T> getEntityType();

    public abstract String getUniqueProperty();

    public abstract String getLabel();
}

这里是 createNativeQuery 和 getSingleResult 方法调用的签名。

public < R > NativeQuery< R > createNativeQuery(String sqlString, Class< R > resultClass)

public R getSingleResult()

getSingleResult() 和 queryForObject(...) 方法签名之间的唯一区别是 queryForObject(...) 方法签名有额外的 < T >,我认为这对return 输入...?

我可以重现你的错误。我可以消除它:

    return session.queryForObject(getEntityType(), query, Collections.emptyMap());

我不能确切地说出为什么这样可以解决问题。但这一定与 queryForObject() 想要通用映射 (Map<String, ?>) 而 Collections.EMPTY_MAP 被声明为原始(非通用)Map.[=15 这一事实有关=]