这是虎年我的第一篇博客,打算就最近多次遇到且踩了多个坑的判断ResultSet是否为空做一个总结整理。
约定 链接到标题
下文获取的ResultSet对象名称规定为re。
尝试一:if(re == null) 链接到标题
我们从某个案例里尝试用debugger来查看空结果集是什么样的:
显然我们从图中可知这个对象是存在的,所以re不可能是null,这个尝试也就失败了。
尝试二:re.isLast()、re.isFirst()、re.isBeforeFirst() 链接到标题
我们已知re传回来有数据时游标指向的是结果集第一行的前一行,但不清楚无数据时光标的指向,所以就拿样例来测试一下吧。
ResultSet re = pstmt.executeQuery("select * from example");
if(re.isLast()){
System.out.println("isLast is true");
}else{
System.out.println("isLast is false");
}
if(re.isFirst()){
System.out.println("isFirst is true");
}else{
System.out.println("isFirst is false");
}
if(re.isBeforeFirst()){
System.out.println("isBeforeFirst is true");
}else{
System.out.println("isBeforeFirst is false");
}
返回为空时 链接到标题
isLast is false
isFirst is false
isBeforeFirst is false
返回非空时 链接到标题
isLast is false
isFirst is false
isBeforeFirst is true
结论 链接到标题
显然isLast
、isFirst
这两个方法是不可以实现我们的需求的,但isBeforeFirst
是可以的。
尝试三:re.next() 链接到标题
关于这种尝试我们也可以用与尝试二类似的方法来测试,但因为这是一个可以改变光标指向的方法,所以我单列了出来。
ResultSet re = pstmt.executeQuery("select * from example");
if(re.next()){
System.out.println("next is true");
}else{
System.out.println("next is false");
}
返回为空时 链接到标题
next is false
返回非空时 链接到标题
next is true
结论 链接到标题
显然next
方法是可以实现需求的,但因为一旦调用了该方法就会使光标移向下一行,如果我们要先判断是否为空,若非空则读取返回数据的话,我们有以下两种策略:
策略一 链接到标题
我们在声明prepareStatement
时传入参数ResultSet.TYPE_SCROLL_INSENSITIVE
,且在判断是否为空后不能忘了用previous
方法将光标移回第一行前。
策略二 链接到标题
在判断结果集是否为空的语句中加上为真时处理第一条记录
ResultSet re = pstmt.executeQuery("select * from example");
if(re.next()){
System.out.println(re.getInt(1));//假设处理语句
}else{
System.out.println("ResultSet is empty");
}
尝试四:if(rs.getRow()==0) 链接到标题
这个尝试的思想的先将光标移至结果集的最后,然后获得此时光标指向的那一行的行号:
ResultSet re = pstmt.executeQuery("select * from example");
rs.last();
if(rs.getRow()==0){
System.out.println("ResultSet is empty");
}
实践可知这是可行的,但也有一个和尝试三一样的问题:此时的光标已经移动了。且调用last
方法本身也需要在声明prepareStatement
时传入参数ResultSet.TYPE_SCROLL_INSENSITIVE
,最终若要读取结果集内的数据则需要调用beforeFirst
方法使光标回到第一行前。