ORA-01000: 超出打开游标的最大数

语言:java,数据库:oracle

开发中通过jdbc做批量删除对象时,出现了如下异常:

java.sql.SQLException: ORA-01000: 超出打开游标的最大数

    at oracle.jdbc.driver.T4CTTIoer.processError(T4CTTIoer.java:440)
    at oracle.jdbc.driver.T4CTTIoer.processError(T4CTTIoer.java:396)
    at oracle.jdbc.driver.T4C8Oall.processError(T4C8Oall.java:837)
    at oracle.jdbc.driver.T4CTTIfun.receive(T4CTTIfun.java:445)

出现这种异常的原因很明确:超出打开游标的最大数。

分析:

Java代码中,执行conn.createStatement()或conn.prepareStatement()新建statement时,相当于在数据库中打开了一个cursor。所以,如果你的createStatement和prepareStatement是在一个循环里面的话,就会非常容易出现这个问题,因为游标在不停的打开却没有关闭。

解决这个问题的方法有两种:

  1. 修改数据库游标cursor上限值

    ORA-01000: 超出打开游标的最大数_第1张图片

    从上图中可以看出oracle当前数据库的游标cursor上限值是300,我们需要修改它的值,如下图所示将cursor值修改为最大值1000

    从上图可以看出oracle的游标值已经被修改为1000了。

    但是仔细思考就可以看出这种方法是治标不治本的,如果代码的循环次数增多,依然会出现当前这个异常,所以最根本的解决方法是重构代码。

  2. 重构java代码

        未重构前的代码片段:

for (long i = 0; i <= 10000; i++) {   
    String sql = "insert into telepnum values(" + i + ")";   
    stmt = con.createStatement(); // 这里是问题的所在   
    stmt.executeUpdate(sql);   
}

        重构后的代码片段:

for (long i = 0; i <= 10000; i++) {   
    String sql = "insert into telepnum values(" + i + ")";   
    stmt = con.createStatement(); // 这里是问题的所在   
    stmt.executeUpdate(sql);
    stmt.close(); //及时关闭statement 
}

        更好的解决方案是将con.createStatement()语句放到循环的外面,一劳永逸。

con = insert.getConnection();   
stmt = con.createStatement(); // 移动到这里,Statemet是可以重用的   
for (long c = a; c <= b; c++) {   
    String sql = "insert into telepnum values(" + c + ")";   
    stmt.executeUpdate(sql);   
}   
stmt.close(); //及时关闭statement


而且,绝大部分情况下,open_cursors只需要设置一个比较小的值,就足够使用了,除非有非常特别的要求。


你可能感兴趣的:(oracle,ORA-01000,最大游标数)