Java JDBC如何将ResultSet游标指向之前的结果集位置?
解决ResultSet退出循环时游标回退的问题
你遇到的需求很清晰:当检测到当前行的DOCID和上一行不匹配时退出while循环,但同时要让ResultSet游标回到上一行的位置。咱们一步步来解决这个问题:
第一步:确保ResultSet支持滚动
默认情况下,JDBC创建的ResultSet是**只能向前遍历(TYPE_FORWARD_ONLY)**的,这种类型无法调用previous()方法回退游标。所以你需要在创建Statement或PreparedStatement时,显式指定可滚动的结果集类型:
如果是普通Statement:
Statement stmt = conn.createStatement( ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY );
如果是PreparedStatement:
PreparedStatement pstmt = conn.prepareStatement( "你的SQL查询语句", ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_READ_ONLY );
其中TYPE_SCROLL_INSENSITIVE表示结果集可以自由滚动,且对数据库的实时修改不敏感;CONCUR_READ_ONLY表示结果集是只读的,完全适配你的使用场景。
第二步:修改循环逻辑,添加游标回退操作
在你执行break退出循环前,调用rs.previous()就能把游标移回上一行。注意要处理这个方法可能抛出的SQLException异常。调整后的代码如下:
while (rs.next()) { docId = rs.getString("DOCID"); System.out.println("In : extractData(1st):docId"+docId); // 检测到ID不匹配时,先回退游标再退出循环 if(previousDocId != null && !previousDocId.equals(docId)){ try { // 将游标移回上一行(最后一个匹配的行) rs.previous(); } catch (SQLException e) { // 根据业务需求处理异常,比如打印日志或向上抛出 e.printStackTrace(); } break; } thisIsAStringArray[0] = firstDocId; String name1 = rs.getString("field_name"); System.out.println("field Name:"+name1); if("address".equals(name1) && 1 == rs.getInt("field_type")){ thisIsAStringArray[1] = rs.getString("field_string"); } previousDocId = docId; }
逻辑说明
当rs.next()返回true时,游标已经指向当前的新行。当你检测到ID不匹配时,此时游标停在不匹配的行上,调用rs.previous()会将游标移回到上一行(也就是最后一个符合条件的行),之后执行break退出循环,后续操作就能正确访问到这一行的数据了。
如果你的业务需要实时感知数据库的修改,可以把结果集类型换成TYPE_SCROLL_SENSITIVE,但如果只是单纯需要游标回退,TYPE_SCROLL_INSENSITIVE的性能会更优。
内容的提问来源于stack exchange,提问作者Ravish
相关产品推荐
相关产品推荐

