首页 > 编程 > Java > 正文

java jdbc学习整理二(接口)

2019-11-08 01:16:51
字体:
来源:转载
供稿:网友

一旦获得一个连接,我们可以与数据库进行交互。在JDBC中Statement, CallableStatementPReparedStatement 接口定义的方法和属性,使可以发送SQL或PL/SQL命令和从数据库接收数据。 它们还定义方法,帮助java和数据库使用SQL数据类型之间转换数据的差异。 下表提供了每个接口的用途概要:

接口 推荐使用
Statement 使用通用访问数据库。当在运行时使用静态SQL语句。 Statement接口不能接受的参数。
PreparedStatement 当计划多次使用SQL语句。 那么可以PreparedStatement接口接收在运行时输入参数。
CallableStatement 当要访问数据库中的存储过程中使用。 CallableStatement对象的接口还可以接受运行时输入参数。

一、Statement

1 创建Statement对象

在可以使用Statement对象执行SQL语句,需要使用Connection对象的createStatement( )方法创建一个,如下面的示例所示:

Connection con = null; //表示数据库的连接对象Class.forName(DBDRIVER);//1、使用CLASS 类加载驱动程序 con = DriverManager.getConnection(DBURL,DBUSER,DBPASS); //2、连接数据库 Statement stmt = null;try { stmt = con.createStatement( ); . . .}catch (SQLException e) { . . .}finally { . . .}

一旦创建了一个Statement对象,然后可以用它来与它的三个执行方法之一执行SQL语句。 (1)boolean execute(String SQL) : 如果ResultSet对象可以被检索返回布尔值true,否则返回false。使用这个方法来执行SQL DDL语句,或当需要使用真正的动态SQL。 (2)int executeUpdate(String SQL) : 返回受影响的SQL语句执行的行的数目。使用此方法来执行,而希望得到一些受影响的行的SQL语句 - 例如,INSERT,UPDATE或DELETE语句。 (3)ResultSet executeQuery(String SQL) : 返回ResultSet对象。当希望得到一个结果集使用此方法,就像使用一个SELECT语句。

2 关闭Statement对象

正如关闭一个Connection对象来保存数据库资源,出于同样的原因,也应该关闭Statement对象。 close()方法简单的调用将完成这项工作。如果关闭了Connection对象首先它会关闭Statement对象也是如此。然而,应该始终明确关闭Statement对象,以确保正确的清除。

Statement stmt = null;try { stmt = conn.createStatement( ); . . .}catch (SQLException e) { . . .}finally { stmt.close();}

close()方法一定要写在finally块中,确保程序抛出异常也可以正常执行。

3 Statement对象实例

import java.sql.Connection;import java.sql.DriverManager;import java.sql.ResultSet;import java.sql.SQLException;import java.sql.Statement;public class StatementJDBCTest { //驱动程序就是之前在classpath中配置的JDBC的驱动程序的JAR 包中 public static final String DBDRIVER = "com.MySQL.jdbc.Driver"; //连接地址是由各个数据库生产商单独提供的,所以需要单独记住 public static final String DBURL = "jdbc:mysql://localhost:3306/test"; //连接数据库的用户名 public static final String DBUSER = "root"; //连接数据库的密码 public static final String DBPASS = "123456"; public static void main(String[] args) { Connection con = null; //表示数据库的连接对象 Statement stmt = null; try { Class.forName(DBDRIVER);//1、使用CLASS 类加载驱动程序 con = DriverManager.getConnection(DBURL,DBUSER,DBPASS); //2、连接数据库 System.out.println(con); stmt = con.createStatement(); String sql = ""; //新增操作 sql = "insert into user (name,cellphone,status,created_time) values ('wangql','1888888888',2,'2017-10-1 12:13:14')"; stmt.executeUpdate(sql); //更新操作 sql = "UPDATE user set name = 'rose2' WHERE id = 7"; Boolean ret = stmt.execute(sql); System.out.println("update: "+ret); //删除操作 sql = "DELETE FROM user WHERE id = 6"; stmt.executeUpdate(sql); //查询操作 sql = "SELECT id,name FROM user "; ResultSet rs = stmt.executeQuery(sql); while(rs.next()){ int id = rs.getInt("id"); String name = rs.getString("name"); System.out.println(id+":"+name); } rs.close(); stmt.close(); con.close(); } catch (ClassNotFoundException e) { e.printStackTrace(); } catch (SQLException e) { e.printStackTrace(); } finally { try{ if(stmt!=null) stmt.close(); }catch(SQLException se2){ se2.printStackTrace(); } try{ if(con!=null) con.close(); }catch(SQLException se){ se.printStackTrace(); } } }}

二、PreparedStatement

PreparedStatement接口扩展了Statement接口,让一个通用的Statement对象增加几个高级功能。statement 提供动态参数的灵活性。PreparedStatement可以预加载sql语句。

1 创建PreparedStatement 对象

Connection con = null; //表示数据库的连接对象Class.forName(DBDRIVER);//1、使用CLASS 类加载驱动程序 con = DriverManager.getConnection(DBURL,DBUSER,DBPASS); //2、连接数据库 PreparedStatement pstmt = null;try { String SQL = "Update user SET name = ? WHERE id = ?"; pstmt = con.prepareStatement(SQL); . . .}catch (SQLException e) { . . .}finally { . . .}

在JDBC中所有的参数都被代表?符号,这是已知的参数标记。在执行SQL语句之前,必须提供值的每一个参数。 setXXX()方法将值绑定到参数,其中XXX表示希望绑定到输入参数值的Java数据类型。如果忘了提供值,将收到一个SQLException。 每个参数标记是由它的序号位置引用。第一标记表示位置1,下一个位置为2 等等。这种方法不同于Java数组索引,以0开始。 所有的Statement对象的方法来与数据库交互execute(),executeQuery()executeUpdate() 也与PreparedStatement对象的工作。然而,该方法被修改为使用SQL语句,可以利用输入的参数。

2 关闭PreparedStatement对象

正如关闭Statement对象,出于同样的原因,也应该关闭的PreparedStatement对象。 close()方法简单的调用将完成这项工作。如果关闭了Connection对象首先它会关闭PreparedStatement对象。然而,应该始终明确关闭PreparedStatement对象,以确保正确的清除。

PreparedStatement pstmt = null;try { String SQL = "Update user SET name = ? WHERE id = ?"; pstmt = conn.prepareStatement(SQL); . . .}catch (SQLException e) { . . .}finally { pstmt.close();}

3 Statement和PreparedStatement的区别

与Statement相比: (1)PreparedStatement接口代表预编译的语句,它主要的优势在于可以减少SQL的编译错误并增加SQL的安全性(减少SQL注射攻击的可能性); (2)PreparedStatement中的SQL语句是可以带参数的,避免了用字符串连接拼接SQL语句的麻烦和不安全; (3)当批量处理SQL或频繁执行相同的查询时,PreparedStatement有明显的性能上的优势,由于数据库可以将编译优化后的SQL语句缓存起来,下次执行相同结构的语句时就会很快(不用再次编译和生成执行计划)。

4 PreparedStatement对象实例

import java.sql.Connection;import java.sql.Date;import java.sql.DriverManager;import java.sql.PreparedStatement;import java.sql.ResultSet;import java.sql.SQLException;public class PreparedStatementJDBCTest { /** * @param args */ //驱动程序就是之前在classpath中配置的JDBC的驱动程序的JAR 包中 public static final String DBDRIVER = "com.mysql.jdbc.Driver"; //连接地址是由各个数据库生产商单独提供的,所以需要单独记住 public static final String DBURL = "jdbc:mysql://localhost:3306/test"; //连接数据库的用户名 public static final String DBUSER = "root"; //连接数据库的密码 public static final String DBPASS = "123456"; public static void main(String[] args) { Connection con = null; //表示数据库的连接对象 PreparedStatement ps = null ; try { Class.forName(DBDRIVER);//1、使用CLASS 类加载驱动程序 con = DriverManager.getConnection(DBURL,DBUSER,DBPASS); //2、连接数据库 System.out.println(con); //新增操作 String insertSql = "insert into user (name,cellphone,status,created_time) values (?,?,?,?)"; ps = con.prepareStatement(insertSql); ps.setString(1, "alex1234"); ps.setString(2, "18522232015"); ps.setInt(3, 1); Date date = new Date(new java.util.Date().getTime()); //构建一个java.sql.Date对象 ps.setDate(4, date); ps.executeUpdate(); //修改操作 String updateSql = "UPDATE user set name =? WHERE id=?"; ps = con.prepareStatement(updateSql); ps.setString(1, "mousihui"); ps.setInt(2, 9); int rows = ps.executeUpdate(); System.out.println("update:"+rows); //删除操作 String deleteSql = "DELETE FROM user WHERE id = ?"; ps = con.prepareStatement(deleteSql); ps.setInt(1, 8); ps.executeUpdate(); //查询操作 String selectSql = "SELECT id,name FROM user "; ResultSet rs = ps.executeQuery(selectSql); while(rs.next()){ int id = rs.getInt("id"); String name = rs.getString("name"); System.out.println(id+":"+name); } con.close();// 3、关闭数据库 ps.close(); rs.close(); } catch (ClassNotFoundException e) { e.printStackTrace(); } catch (SQLException e) { e.printStackTrace(); } finally { try{ if(ps!=null) ps.close(); }catch(SQLException se2){ se2.printStackTrace(); } try{ if(con!=null) con.close(); }catch(SQLException se){ se.printStackTrace(); } } } }

三、CallableStatement

为了提供对存储过程的调用,JDBC API中还提供了CallableStatement接口。存储过程(Stored Procedure)是数据库中一组为了完成特定功能的SQL语句的集合,经编译后存储在数据库中,用户通过指定存储过程的名字并给出参数(如果该存储过程带有参数)来执行它。虽然调用存储过程会在网络开销、安全性、性能上获得很多好处,但是存在如果底层数据库发生迁移时就会有很多麻烦,因为每种数据库的存储过程在书写上存在不少的差别。 注意:在使用CallableStatement对象的时候,我们要确保操作的数据库创建了存储过程,CallableStatement是调用数据库存储过程实现的,不是通过对表修改进行操作的。正如一个Connection对象创建Statement和PreparedStatement对象,它也创造了CallableStatement对象这将被用来执行调用数据库存储过程。

1 创建CallableStatement 对象

先创建mysql存储过程实例

CREATE PROCEDURE getUser(IN p_name CHAR(20)) BEGINIF p_name is null or p_name='' THENSELECT * FROM `user`; ELSESELECT * FROM `user` WHERE NAME LIKE p_name; END IF; END

创建mysql的存储过程有三个类型: 三种类型的参数有:INOUTINOUT。 PreparedStatement对象只使用IN参数。 CallableStatement对象可以使用所有三个。

参数 描述
IN 它的值是在创建SQL语句时未知的参数。将值绑定到与setXXX()方法的参数。
OUT 其值由它返回的SQL语句提供的参数。从OUT参数的getXXX()方法检索值。
INOUT 同时提供输入和输出值的参数。绑定的setXXX()方法的变量,并使用getXXX()方法检索值。

下面的代码片段显示了如何使用该Connection.prepareCall()方法实例化基于上述存储过程CallableStatement对象:

CallableStatement cstmt = null;try { String SQL = "{call getUser(?)}"; cstmt = conn.prepareCall (SQL); . . .}catch (SQLException e) { . . .}finally { . . .}

String变量的SQL表示存储过程,使用参数占位符。 使用CallableStatement对象是就像使用PreparedStatement对象。必须将值绑定到所有的参数执行该语句之前,否则将收到一个SQLException。 如果有IN参数,只要按照适用于PreparedStatement对象相同的规则和技巧;使用对应于要绑定的Java数据类型的setXXX()方法。 当使用OUT和INOUT参数就必须采用额外的CallableStatement及registerOutParameter()方法。registerOutParameter()方法JDBC数据类型绑定到数据类型的存储过程应返回。 一旦调用存储过程,用适当的getXXX()方法的输出参数检索值。这种方法投射SQL类型的值检索到Java数据类型。

2 关闭CallableStatement对象

正如关闭其他Statement对象,出于同样的原因,也应该关闭CallableStatement对象。 close()方法简单的调用将完成这项工作。如果关闭了Connection对象首先它会关闭CallableStatement对象为好。然而,应该始终明确关闭CallableStatement对象,以确保正确的清除。

CallableStatement cstmt = null;try { String SQL = "{call getUser(?)}"; cstmt = conn.prepareCall (SQL); . . .}catch (SQLException e) { . . .}finally { cstmt.close();}

3 CallableStatement对象实例

import java.sql.CallableStatement;import java.sql.Connection;import java.sql.DriverManager;import java.sql.ResultSet;import java.sql.SQLException;public class CallableStatementJDBCTest { //驱动程序就是之前在classpath中配置的JDBC的驱动程序的JAR 包中 public static final String DBDRIVER = "com.mysql.jdbc.Driver"; //连接地址是由各个数据库生产商单独提供的,所以需要单独记住 public static final String DBURL = "jdbc:mysql://localhost:3306/test"; //连接数据库的用户名 public static final String DBUSER = "root"; //连接数据库的密码 public static final String DBPASS = "123456"; public static void main(String[] args) { Connection con = null; CallableStatement stmt = null; try { Class.forName(DBDRIVER);//1、使用CLASS 类加载驱动程序 con = DriverManager.getConnection(DBURL,DBUSER,DBPASS); //2、连接数据库 System.out.println(con); String sql = "{call getUser (?)}"; stmt = con.prepareCall(sql); stmt.setString(1,"alex"); stmt.execute(); ResultSet set = stmt.executeQuery(); while (set.next()) { System.out.println("id:"+set.getString(1)); System.out.println("name:"+set.getString(2)); System.out.println("cellphone:"+set.getString(3)); } set.close(); } catch (ClassNotFoundException e) { e.printStackTrace(); } catch (SQLException e) { e.printStackTrace(); } finally { try{ if(stmt!=null) stmt.close(); }catch(SQLException se2){ se2.printStackTrace(); } try{ if(con!=null) con.close(); }catch(SQLException se){ se.printStackTrace(); } } }}

执行结果:

com.mysql.jdbc.JDBC4Connection@7308c5cid:4name:alexcellphone:18565232510
发表评论 共有条评论
用户名: 密码:
验证码: 匿名发表