比如SQL Server的一个存储过程: create procedure proc_test @q_type int, @value int, @count int output as begin update mytable set value = @value where type = @q_type set @count = @@rowcount select * from mytable where type = @q_type end go 这个存储过程,既有输出参数,又有返回结果集,而用java调用他,两者都要取到,则代码如下: Connection conn = MyConnectionPool.getConnection(); CallableStatement cstmt = conn.prepareCall("{call proc_test(?,?,?)}"); cstmt.setInt(1, type); cstmt.setInt(2, value); cstmt.registerOutParameter(3, java.sql.Types.INTEGER); ResultSet rs = cstmt.executeQuery(); while(rs.next()) { doSomeThingToResultSet(rs); } doSomeThingToOutParameter(cstmt.getInt(3)); rs.close(); cstmt.close(); conn.close(); 其中的关键在于哪儿呢? 必须用cstmt.executeQuery()来取得结果集,用cstmt.execute()然后getResultSet()是取不到的,而executeQuery()能保证先执行update再select; 获得输出参数的cstmt.getInt(3)必须在处理完结果集的所有内容后再执行,如果把上述代码改成如下: ........ doSomeThingToOutParameter(cstmt.getInt(3)); while(rs.next()) { doSomeThingToResultSet(rs); } ........ 后果就是,在rs.next()的时候,会抛出异常:java.sql.SQLException: [Microsoft][SQLServer 2000 Driver for JDBC]Object has been closed. 很有趣,不是么??