ResultSet:exception:set type是TYPE_FORWARD_ONLY – 为什么?

我的代码非常简单:

pstat=con.prepareStatement("select typeid from users where username=? and password=?"); pstat.setString(1, username); pstat.setString(2, password); rs=pstat.executeQuery(); int rowCount=0; while(rs.next()) { rowCount++; } rs.beforeFirst(); if(rowCount>=1) { while(rs.next()) { typeID=rs.getInt(1); } 

但是当执行这段代码时我得到了……

 java.sql.SQLException: Result set type is TYPE_FORWARD_ONLY at sun.jdbc.odbc.JdbcOdbcResultSet.beforeFirst(Unknown Source) at server.ClientImpl.login(ClientImpl.java:57) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) at java.lang.reflect.Method.invoke(Unknown Source) at sun.rmi.server.UnicastServerRef.dispatch(Unknown Source) at sun.rmi.transport.Transport$1.run(Unknown Source) at java.security.AccessController.doPrivileged(Native Method) at sun.rmi.transport.Transport.serviceCall(Unknown Source) at sun.rmi.transport.tcp.TCPTransport.handleMessages(Unknown Source) at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run0(Unknown Source) at sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run(Unknown Source) at java.util.concurrent.ThreadPoolExecutor$Worker.runTask(Unknown Source) at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source) at java.lang.Thread.run(Unknown Source) 

造成这种情况的原因是什么?如何解决?

将您的第一个声明更改为此

 pstat=con.prepareStatement("select typeid from users where username=? and password=?", ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_UPDATABLE); 

这样你就可以前进和后退,所以不用担心

类型TYPE_FORWARD_ONLY意味着您只能向前移动结果集,而不是向后移动,因此当您尝试返回beforeFirst()时会出现exception。 相反,您可以使用以下prepareStatement() ,它接收结果集类型作为参数,或者执行:

  pstat=con.prepareStatement("select typeid from users where username=? and password=?"); pstat.setString(1, username); pstat.setString(2, password); rs=pstat.executeQuery(); int rowCount=0; while(rs.next()) { rowCount++; typeID=rs.getInt(1); } 

您只能使用TYPE_SCROLL_SENSITIVE类型的结果集执行此操作,该结果集定义为“常量,指示可滚动且通常对其他人所做更改敏感的ResultSet对象的类型”。

你需要做类似以下的事情……

 Statement statement = connection.createStatement(ResultSet.TYPE_SCROLL_SENSITIVE, ResultSet.CONCUR_READ_ONLY); 

虽然这个问题很老,但答案并没有老化,今天遇到类似的问题,这就是我接近它的方式,因为这里是Java JDBC驱动程序和PostgreSQL数据库提供的function。 这种情况使用默认参数创建一个Statement对象,系统生成的数据集只能单向移动指针前进,而不是双向移动数据记录指针,前者

语句stmt = dbConn.createStatement();
结果rs = stmt.executeQuery(sql);

变成
语句stmt = dbConn.createStatement(ResultSet.TYPE_SCROLL_INSENSITIVE,ResultSet.CONCUR_READ_ONLY);
结果rs = stmt.executeQuery(sql);

此时生成的rs可以使用rs.first()反向移动指针操作

就像exception所说的那样:你不能在任何其他方向滚动结果集而不是向前滚动。 因此,当您遍历结果集以获取行计数(我甚至不理解您为什么这样做)时,此行将抛出该exception:

 rs.beforeFirst(); 

因为那会向后滚动。

创建语句以便您可以滚动它(例如Google)或删除该行计数。 我建议后者,因为计数似乎没必要。

java.sql.SQLException:结果集类型为TYPE_FORWARD_ONLY

使用JDBC 2.0 API,用户可以灵活地向前或向后移动光标。

您可以通过创建statemnt来删除错误,如下所示

 Statement st = conn.createStatement(ResultSet.TYPE_SCROLL_SENSITIVE,ResultSet.CONCUR_READ_ONLY); 

此外,计算行数的更好方法是

 rs=pstat.executeQuery(); //execute the query rs.last(); //move the cursor to the last row int numberOfRows = rs.getRow(); //get the number of rows rs.beforeFirst(); //back to initial state 

这个问题很老了。 我相信已经找到了解决方案。 但是,我想在这里建议一些与Aditya不同的东西。

 pstat=con.prepareStatement("select typeid from users where username=? and password=?", ResultSet.TYPE_SCROLL_INSENSITIVE, ResultSet.CONCUR_UPDATABLE); 

而不是ResultSet.TYPE_SCROLL_SENSITIVE,我会使用INSENSITIVE

请查看此链接以获取参考

rowCount变量不是必需的。 你在rs上执行两个循环。 只需要第二个循环来获得这部分代码完成的行数:

  while (rs.next()){ typeID=rs.getInt(1); //typeID is the number of rows in the ResultSet }