JDBC Statement, PreparedStatement 和 CallableStatement
获得了数据库连接后,我们就可以与数据库进行交互了。JDBC 中的 Statement, CallableStatement 和 PreparedStatement 三个对象,定义了一系列的方法和属性,可以用来向数据库发送 SQL 命令,接收数据。
接口 | 使用说明 |
---|---|
Statement | 运行静态 SQL 语句时使用,Statement 不能接收输入参数。 |
PreparedStatement | 当计划多次使用某条 SQL 语句时使用,并且 PreparedStatement 可以接收输入参数。 |
CallableStatement | 用来调用数据库的存储过程,CallableStatement 可以接收输入参数。 |
1. Statement 对象
1)创建 Statement 对象
Statement 对象由 Connection 对象的 createStatement( ) 方法创建,用来执行静态 SQL 语句,如下所示:
Statement stmt = null; try { stmt = conn.createStatement( ); . . . } catch (SQLException e) { . . . } finally { . . . }
一旦创建了一个 Statement 对象,然后可以它的三个执行方法之一执行 SQL 语句。
- boolean execute(String SQL) :这个方法常用来执行 SQL DDL 语句。
- int executeUpdate(String SQL) :返回 SQL 语句执行时受影响的行数,常用来执行 INSERT,UPDATE 或 DELETE 语句。
- ResultSet executeQuery(String SQL) : 返回 ResultSet 对象。常用来执行 SELECT 语句,会得到一个结果集 ResultSet。
2)关闭 Statement 对象
正如关闭一个 Connection 对象来释放数据库资源,出于同样的原因,也应该关闭 Statement 对象。
使用 close() 方法关闭 Statement。
Statement stmt = null; try { stmt = conn.createStatement( ); . . . } catch (SQLException e) { . . . } finally { stmt.close(); }
2. PreparedStatement 对象
PreparedStatement 接口扩展了 Statement 接口,给 Statement 对象增加几个高级功能。
它对 SQL 语句进行预编译,效率更高。另外,可以接收动态参数,避免 Statement 中的 SQL 注入问题。
1)创建 PreparedStatement 对象
PreparedStatement pstmt = null; try { String SQL = "Update Employees SET age = ? WHERE id = ?"; pstmt = conn.prepareStatement(SQL); pstmt.setInt(1, 22); . . . } catch (SQLException e) { . . . } finally { . . . }
在 JDBC 中参数使用 ?代表,在执行 SQL 语句之前,必须提供每一个参数的值。
setXXX() 方法将值绑定到参数,其中 XXX 表示希望绑定到输入参数值的 Java 数据类型。如果忘了提供值,将收到一个SQLException。
每个参数标记是由它的序号位置引用。第一标记表示位置 1,下一个位置为 2 等等。这种方法不同于 Java 数组索引,以 0 开始。
2)关闭 PreparedStatement 对象
正如关闭一个 Connection 对象来释放数据库资源,出于同样的原因,也应该关闭 PreparedStatement 对象。
使用 close() 方法关闭 PreparedStatement。
PreparedStatement pstmt = null; try { String SQL = "Update Employees SET age = ? WHERE id = ?"; pstmt = conn.prepareStatement(SQL); . . . } catch (SQLException e) { . . . } finally { pstmt.close(); }
3. CallableStatement 对象
正如一个Connection对象创建Statement和PreparedStatement对象,它也创造了CallableStatement对象这将被用来执行调用数据库存储过程。
1)创建 CallableStatement 对象
假设需要执行以下 Oracle 存储过程:
CREATE OR REPLACE PROCEDURE getEmpName (EMP_ID IN NUMBER, EMP_FIRST OUT VARCHAR) AS BEGIN SELECT first INTO EMP_FIRST FROM Employees WHERE ID = EMP_ID; END;
存储过程有三种类型的参数:IN,OUT和INOUT。 PreparedStatement对象只使用IN参数。 CallableStatement对象可以使用所有三个。
这里是每个的定义:
参数 | 描述 |
---|---|
IN | 它的值是在创建SQL语句时未知的参数。将值绑定到与 setXXX() 方法的参数。 |
OUT | 其值由它返回的SQL语句提供的参数。从 OUT 参数的 getXXX() 方法检索值。 |
INOUT | 同时提供输入和输出值的参数。绑定变量使用 setXXX() 方法,使用 getXXX() 方法检索值。 |
下面的代码显示了使用 Connection.prepareCall() 方法获得存储过程 CallableStatement 对象:
CallableStatement cstmt = null; try { String SQL = "{call getEmpName (?, ?)}"; cstmt = conn.prepareCall (SQL); . . . } catch (SQLException e) { . . . } finally { . . . }
SQL 表示存储过程,里面使用了参数占位符。
使用 CallableStatement 对象是就像使用 PreparedStatement 对象,执行该语句之前,必须将值绑定到所有的参数,否则将收到一个 SQLException。
如果有 IN 参数,只要按照 PreparedStatement 对象相同的规则,使用 setXXX() 方法绑定的 Java 数据类型。
当使用 OUT 和 INOUT 参数就必须采用额外的 CallableStatement 及 registerOutParameter() 方法。registerOutParameter() 方法绑定数据类型到存储过的返回值。
2)关闭 CallableStatement 对象
正如关闭其他 Statement 对象,出于同样的原因,也应该关闭 CallableStatement 对象。
正如关闭一个 Connection 对象来释放数据库资源,出于同样的原因,也应该关闭 CallableStatementv 对象。
使用 close() 方法关闭 CallableStatement。
CallableStatement cstmt = null; try { String SQL = "{call getEmpName (?, ?)}"; cstmt = conn.prepareCall (SQL); . . . } catch (SQLException e) { . . . } finally { cstmt.close(); }
下一章:JDBC ResultSet 结果集
JDBC 执行 SELECT 语句查询后,返回的数据放在结果集中,其中 java.sql.ResultSet 接口表示数据库查询的结果集。ResultSet 对象维护指向结果集中当前行的游标。 结果集是指包含在 ResultSet 对象中的行和列数据。ResultSet 接口的方法可以分为三类:浏览方法、获取方法、更新方法。