PreparedStatement Interface là một interface con của Statement. Nó được sử dụng để thực thi các truy vấn được tham số hóa. Bạn theo dõi ví dụ sau:
String sql="INSERT INTO ten_bang values(?,?,?)";
Như bạn thấy, chúng ta đang truyền các tham số cho values. Giá trị của nó sẽ được thiết lập bằng việc gọi phương thức setter (ví dụ như setShort, setString, …) của PreparedStatement.
Đối tượng PreparedStatement là một đối tượng mà biểu diễn một lệnh SQL được biên dịch trước. Tức là, một lệnh SQL được biên dịch trước và được lưu trữ trong một đối tượng PreparedStatement. Đối tượng này sau đó có thể được sử dụng để thực thi có hiệu quả Statement này nhiều lần.
Lợi thế của PreparedStatement: Sử dụng PreparedStatement giúp tăng hiệu suất, bởi vì truy vấn của bạn sẽ được biên dịch chỉ một lần.
Tạo đối tượng PreparedStatement trong JDBC
Phương thức PrepareStatement() của Connection Interface được sử dụng để trả về đối tượng PreparedStatement. Dưới đây là cú pháp chung:
public PreparedStatement prepareStatement(String query)throws SQLException{}
Để tạo đối tượng PreparedStatement, bạn có thể theo mẫu chung sau:
PreparedStatement pstmt = null; try { String SQL = "UPDATE sinhvienk60 SET diemthi=? WHERE mssv=?"; pstmt = conn.prepareStatement(SQL); . . . } catch (SQLException e) { . . . } finally { . . . }
Tất cả tham số trong JDBC được biểu diễn bởi biểu tượng ? (còn được biết với tên gọi là Parameter Marker). Bạn phải cung cấp các giá trị cho mỗi tham số trước khi thực thi lệnh SQL.
Phương thức setXXX() gắn kết các giá trị tới các tham số, trong đó XXX biểu diễn kiểu dữ liệu trong Java của giá trị mà bạn muốn gắn kết cho tham số đầu vào. Nếu bạn quên cung cấp các giá trị, thì bạn sẽ nhận một SQLException.
Các phương thức của PreparedStatement Interface
Dưới đây là một số phương thức quan trọng của PreparedStatement Interface:
1. public void setInt(int paramIndex, int giaTri)
Thiết lập tham số đã cho tới giá trị nguyên trong Java đã cung cấp. Driver sẽ chuyển đổi giá trị này thành một giá trị nguyên trong SQL khi nó gửi giá trị tới Database.
Trong đó, paramIndex là tham số đầu tiên, tham số thứ hai, …; giaTri là giá trị của tham số.
2. public void setString(int paramIndex, String giaTri)
Thiết lập tham số đã cho thành giá trị String trong Java đã cung cấp. Driver chuyển đổi giá trị này thành một kiểu VARCHAR hoặc LONGVARCHAR (tùy thuộc vào kích cỡ tham số) khi nó gửi giá trị tới Database. (Miêu tả về tham số như trên.)
3. public void setFloat(int paramIndex, float giaTri)
Thiết lập tham số đã cho thành giá trị float trong Java đã cung cấp. Driver chuyển đổi giá trị này thành một giá trị REAL trong SQL khi nó gửi giá trị tới Database. (Miêu tả về tham số như trên.)
4. public void setDouble(int paramIndex, double giaTri)
Thiết lập tham số đã cho thành giá trị double trong Java đã cung cấp. Driver chuyển đổi giá trị này thành một giá trị DOUBLE trong SQL khi nó gửi giá trị tới Database. (Miêu tả về tham số như trên.)
5. public int executeUpdate()
Thực thi truy vấn SQL trong đối tượng PreparedStatement này, mà phải là một lệnh DML (lệnh thao tác dữ liệu) trong SQL như INSERT, UPDATE hoặc DELETE, hoặc một lệnh SQL mà không trả về bất cứ cái gì, chẳng hạn như một lệnh DDL (như CREATE, ALTER, …)
6. public ResultSet executeQuery() throws SQLException
Thực thi truy vấn SQL trong đối tượng PreparedStatement này và trả về đối tượng ResultSet được tạo bởi truy vấn. Phương thức này ném ngoại lệ SQLException và SQLTimeoutException.
Đóng đối tượng PreparedStatement trong JDBC
Giống như khi bạn đóng đối tượng Statement, bạn sử dụng phương thức close(). Tất nhiên, nếu bạn đóng đối tượng Connection, thì nó cũng sẽ đóng đối tượng PreparedStatement. Tuy nhiên, việc đóng đối tượng PreparedStatement một cách tường minh sẽ luôn luôn là một việc thực hành tốt để đảm bảo chắc chắn rằng đối tượng đã được đóng và resource đã được giải phóng.
Dưới đây là mẫu chung để đóng đối tượng PreparedStatement:
PreparedStatement pstmt = null; try { String SQL = "UPDATE sinhvienk60 SET diemthi=? WHERE mssv=?"; pstmt = conn.prepareStatement(SQL); . . . } catch (SQLException e) { . . . } finally { pstmt.close(); }
Ví dụ về đối tượng PreparedStatement trong JDBC
package com.hoctv.jdbc; //Buoc 1: Ban can inport cac package can thiet import java.sql.*; public class ViDuJDBC { // Ten cua driver va dia chi URL cua co so du lieu static final String JDBC_DRIVER = "com.mysql.jdbc.Driver"; static final String DB_URL = "jdbc:mysql://localhost/sinhvien"; // Ten nguoi dung va mat khau cua co so du lieu static final String USER = "root"; static final String PASS = "123456"; public static void main(String[] args) { Connection conn = null; PreparedStatement stmt = null; try{ // Buoc 2: Dang ky Driver Class.forName("com.mysql.jdbc.Driver"); // Buoc 3: Mo mot ket noi System.out.println("Dang ket noi toi co so du lieu ..."); conn = DriverManager.getConnection(DB_URL,USER,PASS); // Buoc 4: Thuc thi truy van System.out.println("Tao cac lenh truy van SQL ..."); String sql = "UPDATE sinhvienk60 SET diemthi=? WHERE mssv=?"; stmt = conn.prepareStatement(sql); // Gan ket cac gia tri vao trong cac tham so. stmt.setInt(1, 6); // Lenh nay se thiet lap diemthi stmt.setInt(2, 1); // Lenh nay se thiet lap mssv // Bay gio cap nhat diem thi cua ban ghi co mssv=1; int rows = stmt.executeUpdate(); System.out.println("So hang bi tac dong : " + rows ); // Lua chon tat ca ban ghi va hien thi chung. sql = "SELECT mssv, ho, ten, diemthi FROM sinhvienk60"; ResultSet rs = stmt.executeQuery(sql); // Buoc 5: Lay du lieu tu Result Set while(rs.next()){ // Lay du lieu boi su dung ten cot int mssv = rs.getInt("mssv"); int diemthi = rs.getInt("diemthi"); String ho = rs.getString("ho"); String ten = rs.getString("ten"); // Hien thi cac gia tri System.out.print("\nMSSV: " + mssv); System.out.print("\nHo: " + ho); System.out.println("\nTen: " + ten); System.out.print("\nDiem Thi: " + diemthi); System.out.print("\n================="); } // Buoc 6: Don sach moi truong va giai phong resource rs.close(); stmt.close(); conn.close(); }catch(SQLException se){ // Xu ly cac loi cho JDBC se.printStackTrace(); }catch(Exception e){ // Xu ly cac loi cho Class.forName e.printStackTrace(); }finally{ // Khoi finally duoc su dung de dong cac resource try{ if(stmt!=null) stmt.close(); }catch(SQLException se2){ } try{ if(conn!=null) conn.close(); }catch(SQLException se){ se.printStackTrace(); }// Ket thuc khoi finally }// Ket thuc khoi try }// Ket thuc main }// Ket thuc ViDuJDBC
Sao chép và dán ví dụ trên trong ViDuJDBC.java, sau đó biên dịch và chạy chương trình Java trên sẽ cho kết quả sau: