一撞蜂、相關(guān)概念
什么是JDBC
JDBC(Java Data Base Connectivity,java數(shù)據(jù)庫(kù)連接)是一種用于執(zhí)行SQL語(yǔ)句的Java API,可以為多種關(guān)系數(shù)據(jù)庫(kù)提供統(tǒng)一訪問俭嘁,它由一組用Java語(yǔ)言編寫的類和接口組成。JDBC提供了一種基準(zhǔn),據(jù)此可以構(gòu)建更高級(jí)的工具和接口,使數(shù)據(jù)庫(kù)開發(fā)人員能夠編寫數(shù)據(jù)庫(kù)應(yīng)用程序遭庶。數(shù)據(jù)庫(kù)驅(qū)動(dòng)
我們安裝好數(shù)據(jù)庫(kù)之后,我們的應(yīng)用程序也是不能直接使用數(shù)據(jù)庫(kù)的稠屠,必須要通過相應(yīng)的數(shù)據(jù)庫(kù)驅(qū)動(dòng)程序峦睡,通過驅(qū)動(dòng)程序去和數(shù)據(jù)庫(kù)打交道。其實(shí)也就是數(shù)據(jù)庫(kù)廠商的JDBC接口實(shí)現(xiàn)完箩,即對(duì)Connection等接口的實(shí)現(xiàn)類的jar文件赐俗。
二、常用接口
Driver接口
Driver接口由數(shù)據(jù)庫(kù)廠家提供弊知,作為java開發(fā)人員,只需要使用Driver接口就可以了粱快。在編程中要連接數(shù)據(jù)庫(kù)秩彤,必須先裝載特定廠商的數(shù)據(jù)庫(kù)驅(qū)動(dòng)程序,不同的數(shù)據(jù)庫(kù)有不同的裝載方法事哭。如:
裝載MySql驅(qū)動(dòng):Class.forName("com.mysql.jdbc.Driver");
裝載Oracle驅(qū)動(dòng):Class.forName("oracle.jdbc.driver.OracleDriver");-
Connection接口
Connection與特定數(shù)據(jù)庫(kù)的連接(會(huì)話)漫雷,在連接上下文中執(zhí)行sql語(yǔ)句并返回結(jié)果。DriverManager.getConnection(url, user, password)方法建立在JDBC URL中定義的數(shù)據(jù)庫(kù)Connection連接上鳍咱。- 連接MySql數(shù)據(jù)庫(kù):Connection conn = - DriverManager.getConnection("jdbc:mysql://host:port/database", "user", "password");
- 連接Oracle數(shù)據(jù)庫(kù):Connection conn = DriverManager.getConnection("jdbc:oracle:thin:@host:port:database", "user", "password");
- 連接SqlServer數(shù)據(jù)庫(kù):Connection conn = DriverManager.getConnection("jdbc:microsoft:sqlserver://host:port; DatabaseName=database", "user", "password");
常用方法:
- createStatement():創(chuàng)建向數(shù)據(jù)庫(kù)發(fā)送sql的statement對(duì)象降盹。
- prepareStatement(sql) :創(chuàng)建向數(shù)據(jù)庫(kù)發(fā)送預(yù)編譯sql的PrepareSatement對(duì)象。
- prepareCall(sql):創(chuàng)建執(zhí)行存儲(chǔ)過程的callableStatement對(duì)象谤辜。
- setAutoCommit(boolean autoCommit):設(shè)置事務(wù)是否自動(dòng)提交蓄坏。
- commit() :在鏈接上提交事務(wù)。
- rollback() :在此鏈接上回滾事務(wù)丑念。
-
Statement接口
用于執(zhí)行靜態(tài)SQL語(yǔ)句并返回它所生成結(jié)果的對(duì)象涡戳。
三種Statement類:- Statement:由createStatement創(chuàng)建,用于發(fā)送簡(jiǎn)單的SQL語(yǔ)句(不帶參數(shù))脯倚。
- PreparedStatement :繼承自Statement接口渔彰,由preparedStatement創(chuàng)建,用于發(fā)送含有一個(gè)或多個(gè)參數(shù)的SQL語(yǔ)句推正。PreparedStatement對(duì)象比Statement對(duì)象的效率更高恍涂,并且可以防止SQL注入,所以我們一般都使用PreparedStatement植榕。
- CallableStatement:繼承自PreparedStatement接口再沧,由方法prepareCall創(chuàng)建,用于調(diào)用存儲(chǔ)過程内贮。
常用Statement方法:
- execute(String sql):運(yùn)行語(yǔ)句产园,返回是否有結(jié)果集
- executeQuery(String sql):運(yùn)行select語(yǔ)句汞斧,返回ResultSet結(jié)果集。
- executeUpdate(String sql):運(yùn)行insert/update/delete操作什燕,返回更新的行數(shù)粘勒。
- addBatch(String sql) :把多條sql語(yǔ)句放到一個(gè)批處理中。
- executeBatch():向數(shù)據(jù)庫(kù)發(fā)送一批sql語(yǔ)句執(zhí)行屎即。
-
ResultSet接口
ResultSet提供檢索不同類型字段的方法庙睡,常用的有:- getString(int index)、getString(String columnName):獲得在數(shù)據(jù)庫(kù)里是varchar技俐、char等類型的數(shù)據(jù)對(duì)象乘陪。
- getFloat(int index)、getFloat(String columnName):獲得在數(shù)據(jù)庫(kù)里是Float類型的數(shù)據(jù)對(duì)象雕擂。
- getDate(int index)啡邑、getDate(String columnName):獲得在數(shù)據(jù)庫(kù)里是Date類型的數(shù)據(jù)。
- getBoolean(int index)井赌、getBoolean(String columnName):獲得在數(shù)據(jù)庫(kù)里是Boolean類型的數(shù)據(jù)谤逼。
- getObject(int index)、getObject(String columnName):獲取在數(shù)據(jù)庫(kù)里任意類型的數(shù)據(jù)仇穗。
ResultSet還提供了對(duì)結(jié)果集進(jìn)行滾動(dòng)的方法:
- next():移動(dòng)到下一行
- Previous():移動(dòng)到前一行
- absolute(int row):移動(dòng)到指定行
- beforeFirst():移動(dòng)resultSet的最前面流部。
- afterLast() :移動(dòng)到resultSet的最后面。
使用后依次關(guān)閉對(duì)象及連接:ResultSet → Statement → Connection
三纹坐、使用JDBC的步驟
加載JDBC驅(qū)動(dòng)程序 → 建立數(shù)據(jù)庫(kù)連接Connection → 創(chuàng)建執(zhí)行SQL的語(yǔ)句Statement → 處理執(zhí)行結(jié)果ResultSet → 釋放資源
注冊(cè)驅(qū)動(dòng) (只做一次)
方式一:Class.forName(“com.MySQL.jdbc.Driver”);
推薦這種方式枝冀,不會(huì)對(duì)具體的驅(qū)動(dòng)類產(chǎn)生依賴。
方式二:DriverManager.registerDriver(com.mysql.jdbc.Driver);
會(huì)造成DriverManager中產(chǎn)生兩個(gè)一樣的驅(qū)動(dòng)耘子,并會(huì)對(duì)具體的驅(qū)動(dòng)類產(chǎn)生依賴果漾。-
建立連接
Connection conn = DriverManager.getConnection(url, user, password);
URL用于標(biāo)識(shí)數(shù)據(jù)庫(kù)的位置,通過URL地址告訴JDBC程序連接哪個(gè)數(shù)據(jù)庫(kù)拴还,URL的寫法為:
其他參數(shù)如:useUnicode=true&characterEncoding=utf8
創(chuàng)建執(zhí)行SQL語(yǔ)句的statement
//Statement
String id = "5";
String sql = "delete from table where id=" + id;
Statement st = conn.createStatement();
st.executeQuery(sql);
//存在sql注入的危險(xiǎn)
//如果用戶傳入的id為“5 or 1=1”跨晴,那么將刪除表中的所有記錄
1 //PreparedStatement 有效的防止sql注入(SQL語(yǔ)句在程序運(yùn)行前已經(jīng)進(jìn)行了預(yù)編譯,當(dāng)運(yùn)行時(shí)動(dòng)態(tài)地把參數(shù)傳給PreprareStatement時(shí),即使參數(shù)里有敏感字符如 or '1=1'也數(shù)據(jù)庫(kù)會(huì)作為一個(gè)參數(shù)一個(gè)字段的屬性值來處理而不會(huì)作為一個(gè)SQL指令)
2 String sql = “insert into user (name,pwd) values(?,?)”;
3 PreparedStatement ps = conn.preparedStatement(sql);
4 ps.setString(1, “col_value”); //占位符順序從1開始
5 ps.setString(2, “123456”); //也可以使用setObject
6 ps.executeQuery();
- 處理執(zhí)行結(jié)果(ResultSet)
1 ResultSet rs = ps.executeQuery();
2 While(rs.next()){
3 rs.getString(“col_name”);
4 rs.getInt(1);
5 //…
6 }
- 釋放資源
//數(shù)據(jù)庫(kù)連接(Connection)非常耗資源片林,盡量晚創(chuàng)建端盆,盡量早的釋放 //都要加try catch 以防前面關(guān)閉出錯(cuò),后面的就不執(zhí)行了
1 try {
2 if (rs != null) {
3 rs.close();
4 }
5 } catch (SQLException e) {
6 e.printStackTrace();
7 } finally {
8 try {
9 if (st != null) {
10 st.close();
11 }
12 } catch (SQLException e) {
13 e.printStackTrace();
14 } finally {
15 try {
16 if (conn != null) {
17 conn.close();
18 }
19 } catch (SQLException e) {
20 e.printStackTrace();
21 }
22 }
23 }
四费封、事務(wù)(ACID特點(diǎn)焕妙、隔離級(jí)別、提交commit弓摘、回滾rollback)
-
事務(wù)基本概率
一組要么同時(shí)執(zhí)行成功焚鹊,要么同時(shí)執(zhí)行失敗的SQL語(yǔ)句。是數(shù)據(jù)庫(kù)操作的一個(gè)單元韧献!
- 事務(wù)開始于:
連接到數(shù)據(jù)庫(kù)上末患,并執(zhí)行一條DML語(yǔ)句(INSERT研叫、UPDATE或DELETE)。
前一個(gè)事務(wù)結(jié)束后璧针,又輸入了另一個(gè)DML語(yǔ)句嚷炉。 - 事務(wù)結(jié)束于:
執(zhí)行COMMIT或ROLLBACK語(yǔ)句。
執(zhí)行一條DDL語(yǔ)句探橱,例如CREATE TABLE語(yǔ)句申屹;在這種情況下,會(huì)自動(dòng)執(zhí)行COMMIT語(yǔ)句隧膏。
執(zhí)行一條DCL語(yǔ)句哗讥,例如GRANT語(yǔ)句;在這種情況下胞枕,會(huì)自動(dòng)執(zhí)行COMMIT語(yǔ)句杆煞。
斷開與數(shù)據(jù)庫(kù)的連接。
執(zhí)行了一條DML語(yǔ)句腐泻,該語(yǔ)句卻失敗了索绪;在這種情況下,會(huì)為這個(gè)無效的DML語(yǔ)句執(zhí)行ROLLBACK語(yǔ)句贫悄。
- 事務(wù)開始于:
-
事務(wù)的四大特點(diǎn)(ACID)
- atomicity(原子性)
表示一個(gè)事務(wù)內(nèi)的所有操作是一個(gè)整體,要么全部成功娘摔,要么全部失斦埂; - consistency(一致性)
表示一個(gè)事務(wù)內(nèi)有一個(gè)操作失敗時(shí)凳寺,所有的更改過的數(shù)據(jù)都必須回滾到修改前的狀態(tài)鸭津。 - isolation(隔離性)
多個(gè)進(jìn)程互不干擾。 - durability(持久性)
持久性事務(wù)完成之后肠缨,它對(duì)于系統(tǒng)的影響是永久性的逆趋。
- atomicity(原子性)
-
事務(wù)隔離級(jí)別從低到高:
- 讀取未提交(Read Uncommitted)
- 讀取已提交(Read Committed)
- 可重復(fù)度(Repeatable Read)
- 序列化(serializble)
批量處理Batch
- 靈活指定SQL中的變量(PreparedStatement)
- 對(duì)存儲(chǔ)過程進(jìn)行調(diào)用(CallableStatement)
- 運(yùn)用事務(wù)處理(Transaction)
- 批處理(Batch)
對(duì)于大量的批處理,建議使用Statement晒奕,因?yàn)镻reparedStatement的預(yù)編譯空間有限闻书,當(dāng)數(shù)據(jù)量特別大時(shí),會(huì)發(fā)生異常脑慧。
- 插入2萬條數(shù)據(jù)的測(cè)試
1 package com.test.jdbc;
2
3 import java.sql.Connection;
4 import java.sql.DriverManager;
5 import java.sql.SQLException;
6 import java.sql.Statement;
7
8 /**
9 * 測(cè)試ResultSet結(jié)果集的基本用法
10 */
11 public class Demo05 {
12 public static void main(String[] args) {
13 Connection conn = null;
14 Statement stmt = null;
15
16 try {
17 Class.forName("com.mysql.jdbc.Driver");
18 conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/testjdbc","root","mysql");
19
20 conn.setAutoCommit(false); //設(shè)為手動(dòng)提交
21
22 long start = System.currentTimeMillis();
23
24 stmt = conn.createStatement();
25 for (int i = 0; i < 20000; i++) {
26 stmt.addBatch("insert into t_user (userName,pwd,regTime) values ('hao" + i + "',666666,now())");
27 }
28 stmt.executeBatch();
29 conn.commit(); //提交事務(wù)
30
31 long end = System.currentTimeMillis();
32 System.out.println("插入200000條數(shù)據(jù)魄眉,耗時(shí)(ms):" + (end - start));
33
34 } catch (ClassNotFoundException e) {
35 e.printStackTrace();
36 } catch (SQLException e) {
37 e.printStackTrace();
38 } finally{
39
40 try {
41 if (stmt!=null) {
42 stmt.close();
43 }
44 } catch (SQLException e) {
45 e.printStackTrace();
46 }
47 try {
48 if (conn!=null) {
49 conn.close();
50 }
51 } catch (SQLException e) {
52 e.printStackTrace();
53 }
54 }
55 }
56 }
- 測(cè)試事務(wù)的基本概念和用法
1 package com.test.jdbc;
2
3 import java.sql.Connection;
4 import java.sql.DriverManager;
5 import java.sql.PreparedStatement;
6 import java.sql.SQLException;
7
8 /**
9 * 測(cè)試事務(wù)的基本概念和用法
10 */
11 public class Demo06 {
12 public static void main(String[] args) {
13 Connection conn = null;
14 PreparedStatement ps1 = null;
15 PreparedStatement ps2 = null;
16
17 try {
18 Class.forName("com.mysql.jdbc.Driver");
19 conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/testjdbc","root","mysql");
20
21 conn.setAutoCommit(false); //JDBC中默認(rèn)是true,自動(dòng)提交事務(wù)
22
23 ps1 = conn.prepareStatement("insert into t_user(userName,pwd)values(?,?)"); //事務(wù)開始
24 ps1.setObject(1, "小高");
25 ps1.setObject(2, "123");
26 ps1.execute();
27 System.out.println("第一次插入");
28
29 try {
30 Thread.sleep(5000);
31 } catch (InterruptedException e) {
32 e.printStackTrace();
33 }
34
35 ps2 = conn.prepareStatement("insert into t_user(userName,pwd)values(?,?,?)"); //模擬執(zhí)行失敗(values的參數(shù)寫成三個(gè)了)
36 //insert時(shí)出現(xiàn)異常,執(zhí)行conn.rollback
37 ps2.setObject(1, "小張");
38 ps2.setObject(2, "678");
39 ps2.execute();
40 System.out.println("第二次插入");
41
42 conn.commit();
43
44 } catch (ClassNotFoundException e) {
45 e.printStackTrace();
46 try {
47 conn.rollback();
48 } catch (SQLException e1) {
49 e1.printStackTrace();
50 }
51 } catch (SQLException e) {
52 e.printStackTrace();
53 } finally{
54
55 try {
56 if (ps1!=null) {
57 ps1.close();
58 }
59 } catch (SQLException e) {
60 e.printStackTrace();
61 }
62 try {
63 if (ps2!=null) {
64 ps2.close();
65 }
66 } catch (SQLException e) {
67 e.printStackTrace();
68 }
69 try {
70 if (conn!=null) {
71 conn.close();
72 }
73 } catch (SQLException e) {
74 e.printStackTrace();
75 }
76 }
77 }
78 }
輸出:
1 第一次插入
2 java.sql.SQLException: No value specified for parameter 3
3 at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:1078)
4 at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:989)
5 at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:975)
6 at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:920)
7 at com.mysql.jdbc.PreparedStatement.checkAllParametersSet(PreparedStatement.java:2611)
8 at com.mysql.jdbc.PreparedStatement.fillSendPacket(PreparedStatement.java:2586)
9 at com.mysql.jdbc.PreparedStatement.fillSendPacket(PreparedStatement.java:2510)
10 at com.mysql.jdbc.PreparedStatement.execute(PreparedStatement.java:1316)
11 at com.test.jdbc.Demo06.main(Demo06.java:39)
五闷袒、時(shí)間處理(Date和Time以及Timestamp區(qū)別坑律、隨機(jī)日期生成)
java.util.Date
- 子類:java.sql.Date
- 子類:java.sql.Time
- 子類:java.sql.Timestamp
測(cè)試時(shí)間處理(java.sql.Date,Time,Timestamp)
1 package com.test.jdbc;
2
3 import java.sql.Connection;
4 import java.sql.DriverManager;
5 import java.sql.PreparedStatement;
6 import java.sql.SQLException;
7 import java.sql.Timestamp;
8 import java.util.Random;
9
10 /**
11 * 測(cè)試時(shí)間處理(java.sql.Date,Time,Timestamp)
12 */
13 public class Demo07 {
14 public static void main(String[] args) {
15 Connection conn = null;
16 PreparedStatement ps = null;
17
18 try {
19 Class.forName("com.mysql.jdbc.Driver");
20 conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/testjdbc","root","mysql");
21
22 for (int i = 0; i < 1000; i++) {
23
24 ps = conn.prepareStatement("insert into t_user(userName,pwd,regTime,lastLoginTime)values(?,?,?,?)");
25 ps.setObject(1, "小高" + i);
26 ps.setObject(2, "123");
27
28 //
29 int random = 1000000000 + new Random().nextInt(1000000000); //隨機(jī)時(shí)間
30
31 java.sql.Date date = new java.sql.Date(System.currentTimeMillis() - random); //插入隨機(jī)時(shí)間
32 java.sql.Timestamp stamp = new Timestamp(System.currentTimeMillis()); //如果需要插入指定時(shí)間,可以使用Calendar囊骤、DateFormat
33 ps.setDate(3, date);
34 ps.setTimestamp(4, stamp);
35 //
36 ps.execute();
37 }
38
39 System.out.println("插入");
40
41 } catch (ClassNotFoundException e) {
42 e.printStackTrace();
43 } catch (SQLException e) {
44 e.printStackTrace();
45 } finally{
46
47 try {
48 if (ps!=null) {
49 ps.close();
50 }
51 } catch (SQLException e) {
52 e.printStackTrace();
53 }
54 try {
55 if (conn!=null) {
56 conn.close();
57 }
58 } catch (SQLException e) {
59 e.printStackTrace();
60 }
61 }
62 }
63 }
測(cè)試時(shí)間處理(java.sql.Date,Time,Timestamp)晃择,取出指定時(shí)間段的數(shù)據(jù)
1 package com.test.jdbc;
2
3 import java.sql.Connection;
4 import java.sql.Date;
5 import java.sql.DriverManager;
6 import java.sql.PreparedStatement;
7 import java.sql.ResultSet;
8 import java.sql.SQLException;
9 import java.text.DateFormat;
10 import java.text.ParseException;
11 import java.text.SimpleDateFormat;
12
13 /**
14 * 測(cè)試時(shí)間處理(java.sql.Date,Time,Timestamp)冀值,取出指定時(shí)間段的數(shù)據(jù)
15 */
16 public class Demo08 {
17
18 /**
19 * 將字符串代表的時(shí)間轉(zhuǎn)為long數(shù)字(格式:yyyy-MM-dd hh:mm:ss)
20 * @param dateStr
21 * @return
22 */
23 public static long str2DateTime(String dateStr){
24 DateFormat format = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
25
26 try {
27 return format.parse(dateStr).getTime();
28 } catch (ParseException e) {
29 e.printStackTrace();
30 return 0;
31 }
32 }
33
34 public static void main(String[] args) {
35 Connection conn = null;
36 PreparedStatement ps = null;
37 ResultSet rs = null;
38
39 try {
40 Class.forName("com.mysql.jdbc.Driver");
41 conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/testjdbc","root","mysql");
42
43 //
44 ps = conn.prepareStatement("select * from t_user where regTime > ? and regTime < ?");
45 java.sql.Date start = new java.sql.Date(str2DateTime("2016-06-20 00:00:00"));
46 java.sql.Date end = new java.sql.Date(str2DateTime("2016-06-24 00:00:00"));
47
48 ps.setObject(1, start);
49 ps.setObject(2, end);
50
51 rs = ps.executeQuery();
52 while(rs.next()){
53 System.out.println(rs.getInt("id") + "--" + rs.getString("userName")+"--"+rs.getDate("regTime"));
54 }
55 //
56
57 } catch (ClassNotFoundException e) {
58 e.printStackTrace();
59 } catch (SQLException e) {
60 e.printStackTrace();
61 } finally{
62
63 try {
64 if (ps!=null) {
65 ps.close();
66 }
67 } catch (SQLException e) {
68 e.printStackTrace();
69 }
70 try {
71 if (conn!=null) {
72 conn.close();
73 }
74 } catch (SQLException e) {
75 e.printStackTrace();
76 }
77 }
78 }
79 }
六、總結(jié)(簡(jiǎn)單封裝宫屠、資源文件properties處理連接信息)
db.properties
1 #右擊該properties文件--properties--Resource--Text file encoding列疗,選中other,選擇其它編碼方式。
2 #如UTF-8或GBK,這樣就能在properties里面輸入中文激况,而不會(huì)自動(dòng)轉(zhuǎn)成Unicode了作彤。
3
4 #java中的properties文件是一種配置文件,主要用于表達(dá)配置信息乌逐。
5 #文件類型為*.properties竭讳,格式為文本文件,文件內(nèi)容是"鍵=值"的格式浙踢。
6 #在properties文件中绢慢,可以用"#"來作注釋
7
8 #MySQL連接配置
9 mysqlDriver=com.mysql.jdbc.Driver
10 mysqlURL=jdbc:mysql://localhost:3306/testjdbc
11 mysqlUser=root
12 mysqlPwd=mysql
13
14 #Oracle連接配置
15 #...
JDBCUtil工具類
1 package com.test.jdbc;
2
3 import java.io.IOException;
4 import java.sql.Connection;
5 import java.sql.DriverManager;
6 import java.sql.ResultSet;
7 import java.sql.SQLException;
8 import java.sql.Statement;
9 import java.util.Properties;
10
11 public class JDBCUtil {
12
13 static Properties pros = null; //可以幫助讀取和處理資源文件中的信息
14
15 static { //加載JDBCUtil類的時(shí)候調(diào)用
16 pros = new Properties();
17 try {
18 pros.load(Thread.currentThread().getContextClassLoader().getResourceAsStream("db.properties"));
19 } catch (IOException e) {
20 e.printStackTrace();
21 }
22 }
23
24 public static Connection getMysqlConn(){
25 try {
26 Class.forName(pros.getProperty("mysqlDriver"));
27 return DriverManager.getConnection(pros.getProperty("mysqlURL"),
28 pros.getProperty("mysqlUser"),pros.getProperty("mysqlPwd"));
29 } catch (Exception e) {
30 e.printStackTrace();
31 return null;
32 }
33 }
34 //可以重載多個(gè),這里就懶得寫了
35 public static void close(ResultSet rs,Statement st,Connection conn){
36
37 try {
38 if (rs!=null) {
39 rs.close();
40 }
41 } catch (SQLException e) {
42 e.printStackTrace();
43 }
44 try {
45 if (st!=null) {
46 st.close();
47 }
48 } catch (SQLException e) {
49 e.printStackTrace();
50 }
51 try {
52 if (conn!=null) {
53 conn.close();
54 }
55 } catch (SQLException e) {
56 e.printStackTrace();
57 }
58 }
59 }
測(cè)試使用JDBCUtil工具類來簡(jiǎn)化JDBC開發(fā)
1 package com.test.jdbc;
2
3 import java.sql.Connection;
4 import java.sql.PreparedStatement;
5 import java.sql.ResultSet;
6
7 /**
8 * 測(cè)試使用JDBCUtil工具類來簡(jiǎn)化JDBC開發(fā)
9 */
10 public class Demo11 {
11 public static void main(String[] args) {
12 Connection conn = null;
13 PreparedStatement ps = null;
14 ResultSet rs = null;
15
16 try {
17 conn = JDBCUtil.getMysqlConn();
18
19 ps = conn.prepareStatement("insert into t_user (userName) values (?)");
20 ps.setString(1, "小高高");
21 ps.execute();
22
23 } catch (Exception e) {
24 e.printStackTrace();
25 } finally{
26 JDBCUtil.close(rs, ps, conn);
27 }
28 }
29 }
參考資料:
https://www.cnblogs.com/erbing/p/5805727.html
https://blog.csdn.net/weixin_46649583/article/details/109611889