Statement
statement執(zhí)行查詢
創(chuàng)建Statement方式:
Connection.createStatement();
執(zhí)行INSERT万栅,UPDATE和DELETE:
Statement.executeUpdate(sql);
通常執(zhí)行DDL
執(zhí)行SELECT:
Statement.executeQuery(sql);
通常執(zhí)行DML
PreparedStatement
開發(fā)中最常用的是PreparedStatement
Statement主要用于執(zhí)行靜態(tài)SQL語句,即內(nèi)容固定不變的SQL語句染簇。
Statement每執(zhí)行一次都要傳入SQL語句編譯一次对室,效率較差模燥。
PreparedStatement是接口,繼承自Statement掩宜。
SQL語句提前編譯蔫骂,executeQuery和executeUpdate不需要傳參∥溃可以有一個或多個IN參數(shù):
IN參數(shù)的值在SQL語句創(chuàng)建時未被指定辽旋,該語句為每個IN參數(shù)保留一個問號作為占位符,每個問號的值必須在語句執(zhí)行之前慧瘤,通過適當(dāng)?shù)膕etInt活setString方法提供戴已。
SQL Injection
對JDBC,SQL注入攻擊只對Statement有效锅减,對PreparedStatement無效糖儡,因?yàn)镻reparedStatement不允許在插入?yún)?shù)時改變SQL語句的邏輯結(jié)構(gòu)
ResultSetMetaData
數(shù)據(jù)結(jié)果集的元數(shù)據(jù),和查詢出來的數(shù)據(jù)集相關(guān)怔匣,從結(jié)果集中獲取
ResultSetMetaData resultSetMetaData = resultSet.getMetaData();
int columnCount = resultSetMetaData.getColumnCount();
String columnName = null;
for (int i = 1; i <= columnCount; i++) {
columnName = resultSetMetaData.getColumnName(i);
System.out.println("columnName = " + columnName);
}
可滾動結(jié)果集
常用的ResultSet握联,初始指針在第一行之前,只能使用next()方法將指針向后移動每瞒,不能反向金闽。可滾動結(jié)果的意味著剿骨,指針可以在結(jié)果集中任意移動代芜。
會發(fā)生大量的IO,性能差浓利,所以不常用挤庇。
創(chuàng)建方法如下:
Statement stmt = conn.createStatement(type,concurrency);
PreparedStatement stmt = conn.prepareStatement(sql, type, concurrency)
type取值:
TYPE_FORWARD_ONLY:只能向前移動钞速,默認(rèn)參數(shù)
TYPE_SCROLL_INSENSITIVE:可滾動,不感知數(shù)據(jù)變化
TYPE_SCROLL_SENSITIVE:可滾動嫡秕,感知數(shù)據(jù)變化
concurrency 取值:
CONCUR_READ_ONLY:只讀
CONCUR_UPDATABLE:可更新