ResultSet返回值问题

北渔。 2014-05-08 09:42:56
如下一个A类中写了一个方法:
	public static ResultSet selectData(String sql){ 
ResultSet rs = null;
Statement st = null;
Connection conn = ConnectionPool.getConnection();
try {
st = conn.createStatement();
rs = st.executeQuery(sql);

return rs;


} catch (SQLException e) {
e.printStackTrace();
}finally{
try{
if(st!=null){
st.close();
ConnectionPool.closeConnection(conn);
}
}catch(SQLException e){
e.printStackTrace();
}
}
return rs;

}


然后又写一个B类,然后调用A类中的方法selectData(),
在B类中我是这样写的:ResultSet rs = DBExecuter.selectData(selectSQL);结果报错,说什么java.sql.SQLException: Operation not allowed after ResultSet closed
是不是A类中我把st关闭了才导致这个问题?问题是我是这样理解的,我新建了一个对象引用ResultSet rs来接收A类中方法返回的ResultSet 对象,这个有错吗
...全文
477 9 打赏 收藏 转发到动态 举报
写回复
用AI写文章
9 条回复
切换为时间正序
请发表友善的回复…
发表回复
咖啡不放糖 2014-05-09
  • 打赏
  • 举报
回复
JDBC.......结果集的返回值
fuxiaoshao 2014-05-08
  • 打赏
  • 举报
回复
看你写的这个意思是不是不想要总复制粘贴这一套东西? 因为rs必须在关闭之前把里面携带的值copy出去。 你可以试试把一个model类的class传进去,然后用反射,将rs查出来的字段匹配model里面的属性名称将rs查出来的每条记录变成传入的class参数的一个对象,然后返回这类对象的集合。 就像hibernate的HibernateTemplate里面的查询方法一样。
suciver 2014-05-08
  • 打赏
  • 举报
回复
引用 3 楼 lu8000 的回复:
引用 2 楼 suciver 的回复:
楼主自己已经找到原因了,你把Statement对象关闭了,那么他所有的ResultSet也会被关闭
那怎么办,我还想做个通用的查询数据库的方法给其它地方用呢,难道我在其它地方调用方法后再关闭rs?
你不要返回ResultSet,你返回成list,就是把ResultSet里面的数据都放到list里面,这样就可以了
北渔。 2014-05-08
  • 打赏
  • 举报
回复
引用 2 楼 suciver 的回复:
楼主自己已经找到原因了,你把Statement对象关闭了,那么他所有的ResultSet也会被关闭
那怎么办,我还想做个通用的查询数据库的方法给其它地方用呢,难道我在其它地方调用方法后再关闭rs?
suciver 2014-05-08
  • 打赏
  • 举报
回复
楼主自己已经找到原因了,你把Statement对象关闭了,那么他所有的ResultSet也会被关闭
葛芮拉 2014-05-08
  • 打赏
  • 举报
回复
应该就是你自己分析的原因了
北渔。 2014-05-08
  • 打赏
  • 举报
回复
引用 4 楼 suciver 的回复:
引用 3 楼 lu8000 的回复:
[quote=引用 2 楼 suciver 的回复:] 楼主自己已经找到原因了,你把Statement对象关闭了,那么他所有的ResultSet也会被关闭
那怎么办,我还想做个通用的查询数据库的方法给其它地方用呢,难道我在其它地方调用方法后再关闭rs?
你不要返回ResultSet,你返回成list,就是把ResultSet里面的数据都放到list里面,这样就可以了[/quote]有理,我怎么想了半天都没想到这个,郁闷
北渔。 2014-05-08
  • 打赏
  • 举报
回复
引用 5 楼 u014602497 的回复:
看你写的这个意思是不是不想要总复制粘贴这一套东西? 因为rs必须在关闭之前把里面携带的值copy出去。 你可以试试把一个model类的class传进去,然后用反射,将rs查出来的字段匹配model里面的属性名称将rs查出来的每条记录变成传入的class参数的一个对象,然后返回这类对象的集合。 就像hibernate的HibernateTemplate里面的查询方法一样。
是的,就是不想总复制那几行代码,想做个通用点
lxbccsu 2014-05-08
  • 打赏
  • 举报
回复
引用 3 楼 lu8000 的回复:
引用 2 楼 suciver 的回复:
楼主自己已经找到原因了,你把Statement对象关闭了,那么他所有的ResultSet也会被关闭
那怎么办,我还想做个通用的查询数据库的方法给其它地方用呢,难道我在其它地方调用方法后再关闭rs?
上面说了你错误; 同时这样通用的方法很难写,一般都是采用ORM框架了; 对于一个简单的查询,也还是可以尝试下,可以使用反射实现; 比如:(没有测试,随意写的,还需你更多的完善)

public static <T> List<T> selectData(
			String sql, 
			Class<T> clz,                               //你的实体Bean类
			HashMap<String, String> columnsToFieldsMap  //数据库表列名到bean字段名的映射
			){ 
		ResultSet rs = null;
		Statement st = null;
		Connection conn = ConnectionPool.getConnection();
		
		List<T> results = new ArrayList<T>();
		
		try {
			st = conn.createStatement();
			rs = st.executeQuery(sql);
			BeanInfo beanInfo = Introspector.getBeanInfo(clz);
			PropertyDescriptor[] beanDesArr = beanInfo.getPropertyDescriptors();
			ResultSetMetaData rsm = rs.getMetaData();
			int size = rsm.getColumnCount();
			
			while(rs.next()){
				T obj = clz.newInstance();
				for(int i = 1; i <= size; i++ ){
					String columnName = rsm.getColumnName(i);
					for(PropertyDescriptor prop: beanDesArr){
						if(prop.getName().equals(columnsToFieldsMap.get(columnName))){
							prop.getWriteMethod().invoke(obj, rs.getObject(i));
						}
					}
				}
				
				results.add(obj);
			}
			return results;
			
		} catch (Exception e) {
			e.printStackTrace();
		}finally{
			try{
				if(st!=null){
					st.close();
					ConnectionPool.closeConnection(conn);
				}
			}catch(SQLException e){
				e.printStackTrace();
			}
		}
		
		return results;
	}

62,621

社区成员

发帖
与我相关
我的任务
社区描述
Java 2 Standard Edition
社区管理员
  • Java SE
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧