public class BaseDao {
protected Connection conn=null;
protected PreparedStatement ps=null;
protected Statement stmt=null;
protected ResultSet rs=null;
public boolean getConnection(){
//读出配置信息
String driver=ConfigManager.getInstance().getString("jdbc.driver_class");
String url=ConfigManager.getInstance().getString("jdbc.connection.url");
String username=ConfigManager.getInstance().getString("jdbc.connection.username");
String password=ConfigManager.getInstance().getString("jdbc.connection.password");
//加载JDBC驱动
try { Class.forName(driver);
//与数据库建立连接
conn=DriverManager.getConnection(url, username, password);
} catch (ClassNotFoundException e) {
e.printStackTrace();
return false;
} catch (SQLException e) {
e.printStackTrace();
return false;
}
return true;
}
//增删改操作
public int executeUpdate(String sql,Object[] params){
int updateRows=0;
getConnection();
try {
ps=conn.prepareStatement(sql);
//填充占位符
for(int i=0;i<params.length;i++){
ps.setObject(i+1, params[i]);
}
//System.out.println(sql);
updateRows=ps.executeUpdate();
} catch (SQLException e) {
e.printStackTrace();
}finally{
closeResource();
}
return updateRows;
}
//查询操作
public ResultSet executeSQL(String sql,Object[] params){
getConnection();
try {
ps=conn.prepareStatement(sql);
//填充占位符
for(int i=0;i<params.length;i++){
ps.setObject(i++, params[i]);
}
rs=ps.executeQuery();
} catch (SQLException e) {
e.printStackTrace();
}finally{
closeResource();
}
return rs;
}
//关闭资源
public boolean closeResource(){
if(rs!=null){
try {
rs.close();
} catch (SQLException e) {
e.printStackTrace();
return false;
}
}
if(ps!=null){
try {
ps.close();
} catch (SQLException e) {
e.printStackTrace();
return false;
}
}
if(conn!=null){
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
return false;
}
}
return true;
}
}
下面是我写的一个接口的实现类
public class BookDaoImpl extends BaseDao implements BookDao {
//获取图书列表
@Override
public List<Book> getBookList() {
List<Book> bookList=new ArrayList<Book>();
try {
//获得Statement对象,执行SQL语句
String sql="select * from books";
Object[] params={};
ResultSet rs=this.executeSQL(sql, params);
//处理执行结果(ResultSet)
while(rs.next()){
System.out.println("运行到这了吗");
int bid =rs.getInt("bid");
String bookname=rs.getString("bookname");
String b_price=rs.getString("b_price");
String image=rs.getString("image");
int stock=rs.getInt("stock");
//将图书信息封装成对象
Book book=new Book();
book.setBid(bid);
book.setBookName(bookname);
book.setPrice(b_price);
book.setImage(image);
book.setStock(stock);
//将图书对象放进集合中
bookList.add(book);
}
} catch (SQLException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}finally{
this.closeResource();
}
return bookList;
}
}
下面是我的 一个测试类 当我运行这个类是总是报下面的异常
public static void main(String[] args) {
BookDaoImpl bookDao=new BookDaoImpl();
List<Book> bookList=bookDao.getBookList();
for(Book book:bookList){
System.out.println(book.getBid()+"\t"+book.getBookName()+"\t"+book.getPrice()+"\t"+book.getStock());
}
异常查了好多资料都说是多线程并发问题,但是我就是不知道出现在那里,求大神帮助啊!
java.sql.SQLException: 关闭的 Resultset: next
at oracle.jdbc.driver.DatabaseError.throwSqlException(DatabaseError.java:112)
at oracle.jdbc.driver.DatabaseError.throwSqlException(DatabaseError.java:146)
at oracle.jdbc.driver.OracleResultSetImpl.next(OracleResultSetImpl.java:175)
at com.bdqn.OA.Dao.Impl.BookDaoImpl.getBookList(BookDaoImpl.java:37)
at com.bdqn.OA.Dao.Impl.BookDaoImpl.main(BookDaoImpl.java:223)
6 个解决方案
#1
你的BookDaoImpl 怎么继承一个BookDao又实现一个BookDao?
ResultSet rs=this.executeSQL(sql, params);
你父类的executeSQL方法已经调用了 closeResource(); 方法
也就是在你调用rs.next()前,已经关闭了ResultSet!
所以就出错了!
ResultSet rs=this.executeSQL(sql, params);
你父类的executeSQL方法已经调用了 closeResource(); 方法
也就是在你调用rs.next()前,已经关闭了ResultSet!
所以就出错了!
#2
executeSQL调用里面关闭了ResultSet
#3
是的,你父类BaseDao里的查询executeSQL方法里不要直接关闭closeResource();就是先别写finally,既然要用resultset,他是一旦和数据库断开,数据集里的数据也就没了,而且在子类也有finally方法,所以父类的就可以省了
#4
二楼解释很到位
#5
你的BookDaoImpl 怎么继承一个BookDao又实现一个BookDao?
ResultSet rs=this.executeSQL(sql, params);
你父类的executeSQL方法已经调用了 closeResource(); 方法
也就是在你调用rs.next()前,已经关闭了ResultSet!
所以就出错了!
我的的BookDaoImpl 是继承一个BaseDao又实现一个BookDao
我现在找到错误原因了,就是因为我在BaseDao工具类里的executeSQL以及executeUpdate方法里的finally里多执行了closeResource关闭资源的方法,使得ResultSet被关闭了,很感谢楼上四位的指正!
ResultSet rs=this.executeSQL(sql, params);
你父类的executeSQL方法已经调用了 closeResource(); 方法
也就是在你调用rs.next()前,已经关闭了ResultSet!
所以就出错了!
我的的BookDaoImpl 是继承一个BaseDao又实现一个BookDao
我现在找到错误原因了,就是因为我在BaseDao工具类里的executeSQL以及executeUpdate方法里的finally里多执行了closeResource关闭资源的方法,使得ResultSet被关闭了,很感谢楼上四位的指正!
#6
我写的和你一样,但我把任何关闭资源都去掉了还是显示关闭的resultset next,怎么回事啊
#1
你的BookDaoImpl 怎么继承一个BookDao又实现一个BookDao?
ResultSet rs=this.executeSQL(sql, params);
你父类的executeSQL方法已经调用了 closeResource(); 方法
也就是在你调用rs.next()前,已经关闭了ResultSet!
所以就出错了!
ResultSet rs=this.executeSQL(sql, params);
你父类的executeSQL方法已经调用了 closeResource(); 方法
也就是在你调用rs.next()前,已经关闭了ResultSet!
所以就出错了!
#2
executeSQL调用里面关闭了ResultSet
#3
是的,你父类BaseDao里的查询executeSQL方法里不要直接关闭closeResource();就是先别写finally,既然要用resultset,他是一旦和数据库断开,数据集里的数据也就没了,而且在子类也有finally方法,所以父类的就可以省了
#4
二楼解释很到位
#5
你的BookDaoImpl 怎么继承一个BookDao又实现一个BookDao?
ResultSet rs=this.executeSQL(sql, params);
你父类的executeSQL方法已经调用了 closeResource(); 方法
也就是在你调用rs.next()前,已经关闭了ResultSet!
所以就出错了!
我的的BookDaoImpl 是继承一个BaseDao又实现一个BookDao
我现在找到错误原因了,就是因为我在BaseDao工具类里的executeSQL以及executeUpdate方法里的finally里多执行了closeResource关闭资源的方法,使得ResultSet被关闭了,很感谢楼上四位的指正!
ResultSet rs=this.executeSQL(sql, params);
你父类的executeSQL方法已经调用了 closeResource(); 方法
也就是在你调用rs.next()前,已经关闭了ResultSet!
所以就出错了!
我的的BookDaoImpl 是继承一个BaseDao又实现一个BookDao
我现在找到错误原因了,就是因为我在BaseDao工具类里的executeSQL以及executeUpdate方法里的finally里多执行了closeResource关闭资源的方法,使得ResultSet被关闭了,很感谢楼上四位的指正!
#6
我写的和你一样,但我把任何关闭资源都去掉了还是显示关闭的resultset next,怎么回事啊