目录
PreparedStatement两大特点:
执行带参数的SQL语句之前需要对占位符‘?’参数进行赋值,PreparedStatement提供setXXX()方法进行赋值

-
- import java.sql.*;
-
- public class PreparedStatementDemo {
- // PreparedStatement:防止sql注入
- private static String diver = "com.mysql.cj.jdbc.Driver";
- private static String url = "jdbc:mysql://localhost:3306/de?serverTimezone=UTC&useSSL=false";
- private static String user = "root";
- private static String password = "root";
-
- public static void main(String[] args) {
- Connection connection = null;
- PreparedStatement pstmt = null;
- ResultSet rs = null;
- int count = 0;
- try {
- connection = DriverManager.getConnection(url,user,password);// 获取数据库连接对象
- String sql_insert = "INSERT INTO tb_student VALUES(?,?,?,?,?,?,?)";
- pstmt = connection.prepareStatement(sql_insert); // 将sql语句进行预编译
- pstmt.setInt(1,2014310103);
- pstmt.setString(2,"新来的");
- pstmt.setString(3,"男");
- pstmt.setString(4,"2022-7-3");
- pstmt.setString(5,"广东");
- pstmt.setString(6,"汉");
- pstmt.setString(7,"AC1234");
- count = pstmt.executeUpdate();
- System.out.println("插入" + count + "条记录");
- } catch (SQLException ex) {
- ex.printStackTrace();
- }
- finally {
- if (rs != null){
- try {
- rs.close();
- } catch (SQLException e) {
- e.printStackTrace();
- }
- }
- if (pstmt != null){
- try {
- pstmt.close();
- } catch (SQLException e) {
- e.printStackTrace();
- }
- }
- if (connection != null){
- try {
- connection.close();
- } catch (SQLException e) {
- e.printStackTrace();
- }
- }
-
- }
- }
- }


CallableStatement接口:用于执行数据库中的存储过程(数据库中一种特殊的预编译的SQL语句)
三种带参数的存储过程:
调用无返回值的存储过程:
{call 存储过程名([参数占位符])}
调用有返回值的存储过程:
{参数占位符 = call 存储过程名([参数占位符])}
示例:
- // 不带参数
- CallableStatement cstmt1 = con.prepareCall("{call P()}");
-
- // 带2个参数
- CallableStatement Cstmt2 = con.prepareCall("{call P(?,?)}");
-
- // 带2个参数且有返回值
- CallableStatement cstmt3 = con.prepareCall("{? = call P(?,?)}");
CallableStatement接口通过setXXX()方法对IN参数进行赋值,通过registerOutParameter()方法对OUT参数进行类型注册
1.OUT参数类型注册的方法
registerOutParameter(int index, int sqlType)
如:注册第3个OUT输出参数是DOUBLE类型
cstmt.registerOutParameter(3, java.sql.Types.DOUBLE)
2.检索结果的获取
CallableStatement接口:提供了getXXX()方法来获取OUT参数的值
IN OUT 参数具有IN和OUT参数的全部功能,需先使用setXXX()对IN OUT参数值进行设置,
再对该IN OUT参数进行类型注册,执行后再使用getXXX()方法来获取执行结果
如:创建带IN和OUT参数的CallableStatement对象
- // 1.获取CallableStatement对象
- CallableStatement cstmt = con.prepareCall("{? = call P(?,?)}");
-
- // 2.注册OUT参数的类型
- cstmt.registerOutParameter(1, java.sql.Types.INTEGER);
-
- // 3.为IN参数赋值
- cstmt.setInt(2, 123);
- cstmt.setString(3, "zhangsan");
-
- // 4.执行
- cstmt.execute();
-
- // 5.根据索引(参数名称)获取返回值
- int res = cstmt.getInt(1);
CallableStatement接口一般用于执行存储过程,返回结果可为多个结果集或多个记录行,所以一般用execure()执行SQL语句
①.准备好一张要操作的数据表

②.创建带有IN、OUT和IN OUT参数的存储过程

③.源代码:
- import java.sql.*;
-
- public class CallableStatementDemo {
- private static String diver = "com.mysql.cj.jdbc.Driver";
- private static String url = "jdbc:mysql://localhost:3306/de?serverTimezone=UTC&useSSL=false";
- private static String user = "root";
- private static String password = "root";
-
- public static void main(String[] args) {
- Connection connection = null;
- CallableStatement cstmt = null;
- try {
- connection = DriverManager.getConnection(url,user,password);// 获取数据库连接对象
-
- // 1.创建CallableStatement对象
- cstmt = connection.prepareCall("{call P(?,?,?)}");
-
- // 2.给IN参数赋值
- cstmt.setInt(1,2013110101);
-
- // 3.给OUT参数注册类型
- cstmt.registerOutParameter(2, Types.VARCHAR);
-
- // 4.给IN OUT参数的IN参数赋值,OUT参数注册类型
- cstmt.setString(3,"This is a good name!");
- cstmt.registerOutParameter(3, Types.VARCHAR);
-
- // 5.执行
- cstmt.execute();
-
- // 6.通过参数索引获取值
- String name = cstmt.getString(2);
- String comment = cstmt.getString(3);
-
- // 7.输出执行结果
- System.out.println(name + "------" + comment);
-
- } catch (SQLException ex) {
- ex.printStackTrace();
- }
- finally {
- if (cstmt != null){
- try {
- cstmt.close();
- } catch (SQLException e) {
- e.printStackTrace();
- }
- }
- if (connection != null){
- try {
- connection.close();
- } catch (SQLException e) {
- e.printStackTrace();
- }
- }
-
- }
- }
- }
