我在练手项目中,编写了一个BaseDao(使用泛型)的基本实现类
如下代码:
public class BaseDaoImpl<T> implements IBaseDao<T> {
private Class<T> entityClass;
// 构造函数: 1. 获取当前运行类的参数化类型; 2. 获取参数化类型中实际类型的定义(class)
public BaseDaoImpl() {
entityClass = (Class<T>) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0];
}
public Session getSession() {
return HibernateSessionFactory.getSession();
}
public void closeSession(){
HibernateSessionFactory.closeSession();
}
/* 省略本分代码 */
}
但是我在struts2的框架 UserAction里直接使用了如上基本实现类BaseDaoImpl<T>
//这就是出错的原因
private BaseDao<HouseUser> dao = new BaseDaoImpl<HouseUser>();
导致在jsp页面跳转到UserAction就会报 错
java.lang.Class cannot be cast to java.lang.reflect.ParameterizedType
----------------------------------------------------------------------------------
最后找到问题所在
原因是我运行时传参,在UserAction使用 BaseDao 的基本实现 BaseDaoImpl<T>时,才确定泛型类型
这样就会出错
因为 泛型类型 是要在编译时就确定的,如果运行时去设置泛型类型,编译器就会出现类型转换错误
----------------------------------------------------------------------------------
解决办法:
先 编写 接口继承 我的BaseDao,给他指明类型
public interface IUserDao extends BaseDaoImpl<User> {
/* 省略部分代码 */
public void add(User user, Integer groupid);
}
在 编写上面接口的实现类
public class UseDaoImpl extends BaseDaoImpl<User> implements IUserDao{
/*
这里去实现你的 UserDao
*/
}
----------------------------------------------
就是要在编译时就确定 BaseDaoImpl<User> 里是类型
java的泛型在编译的时候可以保证,但是运行的时候泛型是会被擦除的。