在使用Java进行数据库连接操作过程中,尤其是JDBC操作的时候,需要大量的使用游标。偶尔会出现以下异常:
ORA-01000: 超出打开游标的最大数。
网络搜索了一下,说是使用游标的时候没有关闭连接。尤其是在循环使用的时候,会出现问题。
于是我检查了下我的代码,结构如下:
/** 删除表主键* */
public static void deletePrimaryKey(String tableName) {
Connection con = null;
PreparedStatement pstmt = null;
ResultSet rs = null;
String sql = "select SQL FROM TABLE"
try {
con = DataSourceFinder.getCONN();
pstmt = con.prepareStatement(sql);
rs = pstmt.executeQuery();
if (rs.next()) {
sql = rs.getString(1);
pstmt = con.prepareStatement(sql);
pstmt.execute();
}
} catch (Exception e) {
e.printStackTrace();
} finally {
DataSourceFinder.close(pstmt);
DataSourceFinder.close(con);
}
}
粗了看了下,使用的连接都有关闭!都放到finally块中进行关闭。
仔细检查,发现里面进行了两次:pstmt=con.prepareStatement调用。这是不允许的。
于是我把这个方法重构了下,形成两个方法体:
/** 删除表主键* */
public static void deletePrimaryKey(String tableName) {
Connection con = null;
PreparedStatement pstmt = null;
final String sql = getDeleteSQL(tableName);
if(sql!=null){
try {
con = DataSourceFinder.getCONN();
pstmt = con.prepareStatement(sql);
pstmt.executeUpdate();
} catch (Exception e) {
e.printStackTrace();
} finally {
DataSourceFinder.close(pstmt);
DataSourceFinder.close(con);
}
}
}
/**
*
* @description 获取删除主键的SQL语句
* @param tableName 数据表
* @return SQL语句
*/
public static String getDeleteSQL(String tableName){
Connection con = null;
PreparedStatement pstmt = null;
ResultSet rs = null;
final String sql = "select SQL FROM TABLE";
String result = null;
try {
con = DataSourceFinder.getCONN();
pstmt = con.prepareStatement(sql);
rs = pstmt.executeQuery();
if (rs.next()) {
result = rs.getString(1);
}
} catch (Exception e) {
e.printStackTrace();
} finally {
DataSourceFinder.close(pstmt);
DataSourceFinder.close(con);
}
return result;
}
这样的修改可以避免ORA-01000: 超出打开游标的最大数的异常。
但是这样的修改,能不能带来更高的效率,这个本人还在研究当中。
起码以上的一个重构方法,可以实现了一个方法一个作用的目的。并且保证Connection在一次连接中没有做多余的事情。