簡體   English   中英

道課的通用課

[英]Generic class for the Dao classes

我正在嘗試設置一個通用類,該通用類將作為我的應用程序中所有Dao類的基類,但是我現在遇到錯誤。 我的通用類是這樣定義的;

public class Dao<E> {

    private final E entity;

    @Autowired
    SessionFactory sessionFactory;

    protected Session getCurrentSession(){
        return sessionFactory.getCurrentSession();
    }

    public Dao(E entity) {  
        this.entity = entity;
    }

    public E getEntity() {
        return this.entity;
    }

    @Transactional
    public boolean persist(E transientInstance) {
        try {
            sessionFactory.getCurrentSession().persist(transientInstance);
            return true;
        } catch (RuntimeException re) {
            return false;
        }
    }

    @Transactional
    public boolean remove(E transientInstance) {
        try {
            sessionFactory.getCurrentSession().delete(transientInstance);
            return true;
        } catch (RuntimeException re) {
            return false;
        }
    }

    @SuppressWarnings("unchecked")
    @Transactional
    public E merge(E detachedInstance) {
        try {
            E result = (E) sessionFactory.getCurrentSession().merge(detachedInstance);
            return result;
        } catch (RuntimeException re) {
            return null;
        }
    }

    @Transactional
    public E findById(int id) {
        try {
            E instance = (E) sessionFactory.getCurrentSession().get(E, id);
            return instance;
        } catch (RuntimeException re) {
            return null;
        }
    }

    @SuppressWarnings("unchecked")
    @Transactional
    public E findByUsername(String username) {
        try {
            E instance = (E) sessionFactory.getCurrentSession().createCriteria(E, username).add(Restrictions.like("login", username)).list().get(0);
            return instance;
        } catch (RuntimeException re) {
            return null;
        }
    }

    @SuppressWarnings("unchecked")
    @Transactional
    public List<E> findAll() {
        try {
            List<E> instance = sessionFactory.getCurrentSession().createCriteria(E).list();
            return instance;
        } catch (RuntimeException re) {
            return null;
        }
    }

}

帶有錯誤的方法是最后三個方法,它們在實現中與get()和createCriteria()對E的引用有關 (錯誤是E無法解析為變量 )。 通常,當我不使用這種基於泛型的方法時,我會使用類似“ Usuario.class”的名稱。

任何人都知道如何在我的通用類中解決此錯誤(如果可能的話)。

首先,類型參數E不等於Class的實例。 其次,由於Java中的類型擦除,關於E的所有內容在運行時都會丟失。 但它表明,作為參數傳遞給構造函數的entity是在嘗試查詢類時使用的類型標記。 因此,請如下更改方法:

@Transactional
public E findById(int id) {
    try {
        E instance = (E) sessionFactory.getCurrentSession().get(entity.getClass(), id);
        return instance;
    } catch (RuntimeException re) {
        return null;
    }
}

@SuppressWarnings("unchecked")
@Transactional
public E findByUsername(String username) {
    try {
        E instance = (E) sessionFactory.getCurrentSession().createCriteria(entity.getClass(), username).add(Restrictions.like("login", username)).list().get(0);
        return instance;
    } catch (RuntimeException re) {
        return null;
    }
}

@SuppressWarnings("unchecked")
@Transactional
public List<E> findAll() {
    try {
        List<E> instance = sessionFactory.getCurrentSession().createCriteria(entity.getClass()).list();
        return instance;
    } catch (RuntimeException re) {
        return null;
    }
}

或者,如果entity不是您的類型令牌,則向構造函數添加參數Class<E> clazz ,如下所示:

private final E entity;
private final Class<E> clazz;

public Dao(E entity, Class<E> clazz) {  
    this.entity = entity;
    this.clazz = clazz;
}

並在建議的方法中使用clazz而不是entity.getClass()

只需添加上面的答案即可。 如果您不想將參數傳遞給構造函數,則可以執行以下操作:

private Class<T> type;

public Dao(){

    Type t = getClass().getGenericSuperclass();
    ParameterizedType pt = (ParameterizedType) t;
    type = (Class<T>) pt.getActualTypeArguments()[0];
}

然后在進行查詢時在條件中引用類型。

附錄:從DAO層中刪除@Transactional批注,@ @Transactional屬於您的服務層

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM