溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點(diǎn)擊 登錄注冊 即表示同意《億速云用戶服務(wù)條款》

如何使用Java中的JDBC

發(fā)布時(shí)間:2020-08-04 13:54:51 來源:億速云 閱讀:199 作者:小豬 欄目:編程語言

這篇文章主要講解了如何使用Java中的JDBC,內(nèi)容清晰明了,對此有興趣的小伙伴可以學(xué)習(xí)一下,相信大家閱讀完之后會有幫助。

什么是JDBC:

  • JDBC全稱Java Database Connectivity
  • JDBC可以通過載入不同的數(shù)據(jù)庫的“驅(qū)動程序”而與不同的數(shù)據(jù)庫進(jìn)行連接。

JDBC的優(yōu)點(diǎn):

  • 使用的驅(qū)動不同,即可連接不同的數(shù)據(jù)庫。
  • 使用同一套操作來操作不同的數(shù)據(jù)庫
  • 如果每一個(gè)數(shù)據(jù)庫java都制訂一套連接方式,那么當(dāng)不同的數(shù)據(jù)庫更新的時(shí)候,java也需要更新自己的代碼,而使用jdbc,使用同一套代碼來操作,使用不同的驅(qū)動程序(驅(qū)動程序由數(shù)據(jù)庫廠商提供)來連接,這使得可以連接不同的數(shù)據(jù)庫。

JDBC的使用:

導(dǎo)入對應(yīng)數(shù)據(jù)庫的驅(qū)動類:

  • 1.在對應(yīng)的數(shù)據(jù)庫廠商網(wǎng)站獲取對應(yīng)的jar包
  • 2.將對應(yīng)的jar包添加到引用。
    • 在eclipse中可以將jar包導(dǎo)入一個(gè)文件夾后,右鍵Build Path -> add to path就可以將jar包添加到當(dāng)前項(xiàng)目引用的庫里面。如何使用Java中的JDBC

加載驅(qū)動:

  • 如何使用Java中的JDBC

PS:

  • 在上面的forName中,執(zhí)行了注冊驅(qū)動,注冊驅(qū)動這個(gè)代碼被定義在驅(qū)動類的靜態(tài)代碼塊中。
  • 對于一些新手,使用的方法可能是如何使用Java中的JDBC,對于這種情況,那么他可以使用driver或DriverManager.getConnection來獲取數(shù)據(jù)庫連接對象;而對于另外一些新手,他們可能會使用如何使用Java中的JDBC,然后再通過DriverManager.getConnection來獲取數(shù)據(jù)庫連接對象。但本質(zhì)上,這是一種浪費(fèi),因?yàn)殪o態(tài)代碼塊中已經(jīng)靜態(tài)生成了一個(gè)驅(qū)動對象并使用DriverManager.registerDriver注冊了,所以上面兩種都是浪費(fèi)。使用forName后,可以使用DriverManager.getConnection來獲取數(shù)據(jù)庫連接對象。

獲取連接:

  • 在考慮使用forName節(jié)省資源后,下面介紹的獲取連接的方法使用的是DriverManager.getConnection如何使用Java中的JDBC
  • getConnection需要參數(shù)  
    • url:定義了連接的數(shù)據(jù)庫的路徑    
      • jdbc協(xié)議:數(shù)據(jù)庫子協(xié)議:主機(jī)[:端口][/連接的數(shù)據(jù)庫]  【[]代表可選的】
      • 例如:jdbc:mysql://localhost:3306/test如何使用Java中的JDBC
    • 配置流Properties:定義了連接數(shù)據(jù)庫的方式,一般至少包含user和password
    • 不使用配置流時(shí),傳入user和password
    • 如果使用匿名登錄,則只傳入url

如何使用Java中的JDBC

執(zhí)行SQL語句:

JDBC執(zhí)行SQL語句的方式主要有三種:

1.使用Statement執(zhí)行sql語句

2.使用PreparedStatement執(zhí)行sql語句

3.使用CallableStatement執(zhí)行sql語句

上面的Statement、PerPareStatement、Callalestatement都可以使用連接對象來獲取。

如何使用Java中的JDBC

  • 使用Statement執(zhí)行語句
    • Statement對象的獲取可以使用createStatement()來獲取
    • 獲取Statement對象后,對于查詢類的sql語句使用:executeQuery(sql),sql是一個(gè)字符串sql語句,返回結(jié)果是一個(gè)結(jié)果集【如果獲取結(jié)果看下面的結(jié)果部分】
    • 對于更新類(插入、修改、刪除、更新)的語句使用:executeUpdate(sql),sql是一個(gè)字符串sql語句,返回結(jié)果是一個(gè)整數(shù)(受影響的行數(shù))

如何使用Java中的JDBC

  • 使用PreparedStatement執(zhí)行語句
    • PreparedStatement對象的獲取可以使用prepareStatement(sql)來獲取,注意的是需要傳入一條sql語句
    • PreparedStatement的功能類似Statement,但不同的是PreparedStatement可以使用占位符,它是由占位符標(biāo)識需要輸入數(shù)據(jù)的位置,然后再逐一填入數(shù)據(jù)。當(dāng)然,PreparedStatement也可以執(zhí)行沒有占位符的sql語句
      • 使用占位符后,使用setStringsetInt等方法來設(shè)置每一位的數(shù)據(jù)?!居懈鞣N對應(yīng)數(shù)據(jù)類型的設(shè)置方法,比如還有setFloat
        • setXXX方法中,第一個(gè)參數(shù)是位置,第二個(gè)是數(shù)據(jù)
    • 獲取Statement對象后,對于查詢類的sql語句使用:executeQuery(),返回結(jié)果是一個(gè)結(jié)果集【如果獲取結(jié)果看下面的結(jié)果部分】
    • 對于更新類(插入、修改、刪除、更新)的語句使用:executeUpdate(),返回結(jié)果是一個(gè)整數(shù)(受影響的行數(shù))
    • 補(bǔ)充:
      • 對于有sql緩存池的數(shù)據(jù)庫,PreparedStatement的效率要高于Statement【有興趣的自查】

如何使用Java中的JDBC

  • 使用CallableStatement執(zhí)行語句
    • CallableStatement主要用來調(diào)用存儲過程
    • 對于輸出參數(shù),需要使用registerOutParameter注冊,第一個(gè)參數(shù)是位置,第二個(gè)參數(shù)是參數(shù)類型(使用Types.xxx)
    • 注冊之后,想要獲取輸出參數(shù),可以使用CallableStatement對象自身的getXXX方法來獲取

定義的存儲過程示例:

如何使用Java中的JDBC

使用:

如何使用Java中的JDBC

獲取返回:

  • 返回結(jié)果是一個(gè)結(jié)果集,它有一個(gè)光標(biāo)指向結(jié)果的每一行,最開始它不指向結(jié)果,第一次執(zhí)行next()后,它指向第一行結(jié)果,繼續(xù)執(zhí)行next(),他會繼續(xù)指向下一行。next的返回結(jié)果是布爾值,它可以用來判斷是否有下一行。
    • 對于每一行結(jié)果,可以使用getXXX方法(參照下面)來獲取某一列的結(jié)果,getXXX方法的參數(shù)可以為字段名,也可以為索引號(從1開始)

如何使用Java中的JDBC

如何使用Java中的JDBC

關(guān)閉連接:

  • 后開啟的需要先關(guān)閉,Statement、Connection、ResultSet都是需要關(guān)閉的
  • 注意:關(guān)閉之前需要留心檢查是否為null

如何使用Java中的JDBC


事務(wù)

不了解事務(wù)是什么的,可以看一下我的另外一篇博文:mysql之事務(wù)管理

設(shè)置事務(wù)管理:

連接對象.setAutoCommit(boolean)【當(dāng)參數(shù)為true時(shí),代表允許自動提交(事務(wù)管理是關(guān)閉的,每一條命令都會自動提交);當(dāng)為false時(shí),代表不允許自動提交,命令會在執(zhí)行commit之后再統(tǒng)一提交(開啟事務(wù)管理的)】

提交事務(wù):

連接對象.commit()

回滾事務(wù):

連接對象.rollback()

例子:

以銀行轉(zhuǎn)賬為例,張三轉(zhuǎn)給李四100元,執(zhí)行事務(wù)后,如果運(yùn)行出錯(cuò)將不會提交數(shù)據(jù)到數(shù)據(jù)庫:

如何使用Java中的JDBC

如何使用Java中的JDBC

補(bǔ)充:

  • 有些時(shí)候,在開發(fā)中是不會把兩個(gè)操作放到一個(gè)地方的(在Javaweb中開發(fā)中存在service層和dao層。可以這么說,servlet是飯店前臺,service層就是包廂里點(diǎn)菜的服務(wù)員(客戶需要什么菜,他負(fù)責(zé)告訴后廚),dao層就是真正做菜的后廚(dao層通常是數(shù)據(jù)庫方面的操作)。服務(wù)員一次性把需要的菜告訴后廚),這樣耦合性較高,通常需要把它們放到單獨(dú)的地方去(就好比一個(gè)大廚做好幾樣菜會很忙,通常都會分工好),比如加錢是一個(gè)函數(shù),減錢是一個(gè)函數(shù)。把他們分開后,兩個(gè)函數(shù)之間的Connection不同的話,就會無法統(tǒng)一進(jìn)行事務(wù)管理。通常有兩個(gè)解決方法:1.把同一個(gè)Connection對象傳給這兩個(gè)參數(shù)。2.利用Threadlocal類,把Connection對象存進(jìn)去,兩個(gè)要用的時(shí)候再取,取的是同一個(gè)對象。【這里可能不容易理解,只是做個(gè)提醒,可以不理解。】

數(shù)據(jù)庫連接池

  • 連接池的意義就是提前創(chuàng)建連接,避免需要使用時(shí)再申請連接造成的重復(fù)申請資源造成的浪費(fèi)。
  • 連接池負(fù)責(zé)在需要的時(shí)候分發(fā)連接,使用者釋放連接時(shí)需要放回到連接池中。

連接池可以自定義,當(dāng)然常用的一般都是選擇采用第三方開源的連接池,想了解如何自定義連接池的可以自查,下面給出的是兩個(gè)常用的連接池的用法。

DBCP:

首先,使用DBCP連接池需要導(dǎo)入包:commons-dbcp.jar和commons-pool.jar【如果需要日志功能,還需要commons-logging-1.2.jar ,這里不講述】

DBCP根據(jù)配置方式,下面給出兩種使用方法:

1.手動配置法:

  1. 創(chuàng)建BasicDataSource對象: BasicDataSource dataSource = new BasicDataSource();
  2. 配置BasicDataSource對象:(少用)調(diào)用對應(yīng)函數(shù)配置,例如dataSource.setDriverClassName("com.mysql.jdbc.Driver");
  3. 得到連接對象:Connection conn = ds.getConnection();
  4. 操作數(shù)據(jù)庫。(得到數(shù)據(jù)庫連接對象后,就可以像以前一樣去操作數(shù)據(jù)庫了)

如何使用Java中的JDBC

2.配置文件配置法:

  1. 創(chuàng)建BasicDataSourceFactory對象:BasicDataSourceFactory factory = new BasicDataSourceFactory();
  2. 利用BasicDataSourceFactory對象的createDataSource函數(shù)讀取配置文件配置DataSource對象:DataSource dataSource = factory.createDataSource(properties);【配置文件能用哪些參數(shù)可以參考這個(gè)文檔:http://commons.apache.org/proper/commons-dbcp/configuration.html】
  3. 得到連接對象:Connection conn = ds.getConnection();
  4. 操作數(shù)據(jù)庫。(得到數(shù)據(jù)庫連接對象后,就可以像以前一樣去操作數(shù)據(jù)庫了)

如何使用Java中的JDBC

當(dāng)使用完畢后,像往常一樣調(diào)用close關(guān)閉連接即可【這里通過連接池獲取的Connection對象已經(jīng)封裝過了,使用close函數(shù)相當(dāng)于放回連接池中】

常用的dbcp.properties的配置信息:

#連接設(shè)置
driverClassName=com.mysql.jdbc.Driver
url=jdbc:mysql://localhost:3306/jdbc
username=root
password=

#<!-- 初始化連接 -->
initialSize=10

#最大連接數(shù)量
maxActive=50

#<!-- 最大空閑連接 -->
maxIdle=20

#<!-- 最小空閑連接 -->
minIdle=5

#<!-- 超時(shí)等待時(shí)間以毫秒為單位 6000毫秒/1000等于60秒 -->
maxWait=60000


#JDBC驅(qū)動建立連接時(shí)附帶的連接屬性屬性的格式必須為這樣:[屬性名=property;]
#注意:"user" 與 "password" 兩個(gè)屬性會被明確地傳遞,因此這里不需要包含他們。
connectionProperties=useUnicode=true;characterEncoding=gbk

#指定由連接池所創(chuàng)建的連接的自動提交(auto-commit)狀態(tài)。
defaultAutoCommit=true

#driver default 指定由連接池所創(chuàng)建的連接的事務(wù)級別(TransactionIsolation)。
#可用值為下列之一:(詳情可見javadoc。)NONE,READ_UNCOMMITTED, READ_COMMITTED, REPEATABLE_READ, SERIALIZABLE
defaultTransactionIsolation=READ_UNCOMMITTED

C3P0:

首先,使用C3P0連接池需要導(dǎo)入包:c3p0-0.9.1.2.jar【還有擴(kuò)展包如c3p0-oracle-thin-extras-0.9.1.2.jar,這里不講】

手動配置法:

  1. 創(chuàng)建ComboPooledDataSource對象:ComboPooledDataSource dataSource = new ComboPooledDataSource();
  2. 調(diào)用對應(yīng)函數(shù)配置對應(yīng)屬性

如何使用Java中的JDBC

配置文件配置法:

  1. 創(chuàng)建配置文件,c3p0的配置文件名字是固定的,必須是c3p0.properties或c3p0-config.xml,否則識別不了。配置文件的寫法看下面【配置文件存儲的位置:1.能在classpath中獲取到的目錄(比如工程的src目錄)、2.WEB-INF/classes、3.某些類似功能的路徑】
  2. 創(chuàng)建ComboPooledDataSource對象【如果有配置文件,那么會讀取配置文件來配置ComboPooledDataSource對象】
  3. 獲取連接
  4. 執(zhí)行sql語句

如何使用Java中的JDBC

當(dāng)你使用完后,Connection對象調(diào)用close函數(shù),就會把連接釋放會連接池中【這里通過連接池獲取的Connection對象已經(jīng)封裝過了,使用close函數(shù)相當(dāng)于放回連接池中】

配置文件c3p0-config.xml的寫法:

<c3p0-config>
  <default-config>
    <property name="driverClass">com.mysql.jdbc.Driver</property>
    <property name="jdbcUrl">jdbc:mysql://localhost/bank</property>
    <property name="user">root</property>
    <property name="password">123456</property>
    <!-- 下面的是額外的配置,如最大連接數(shù),連接池大小。。 
    <property name="initialPoolSize">10</property> 
    <property name="maxIdleTime">30</property> <property name="maxPoolSize">100</property> 
    <property name="minPoolSize">10</property> <property name="maxStatements">200</property> 
    -->

  </default-config>
  <!-- 上面是默認(rèn)的,如果不給參數(shù),默認(rèn)是上面的; -->
  <!-- 下面的是單獨(dú)的,在創(chuàng)建對象時(shí)把下面name中的那個(gè)值賦給對象的構(gòu)造函數(shù),那么將使用下面的配置 -->
  <named-config name="student">
    <property name="driverClass">com.mysql.jdbc.Driver</property>
    <property name="jdbcUrl">jdbc:mysql://localhost/student</property>
    <property name="user">root</property>
    <property name="password">123456</property>
  </named-config>

</c3p0-config>

配置文件c3p0.properties的寫法:

c3p0.driverClass=com.mysql.jdbc.Driver
c3p0.jdbcUrl=jdbc:mysql://localhost/bank
c3p0.user=root
c3p0.password=123456

想更詳細(xì)的了解c3p0,可以參考官方文檔:https://www.mchange.com/projects/c3p0/index.html

怎樣去配置c3p0連接池,什么英語代表什么意思,具體請參考:https://www.mchange.com/projects/c3p0/index.html

補(bǔ)充:

  • 事實(shí)上DBCP和c3p0還有不少使用方法,上面只講解了常用的。

DbUtils

  • DbUtils是apache旗下的一個(gè)操作數(shù)據(jù)庫的工具
  • DbUtils可以簡化我們對數(shù)據(jù)庫的CRUD操作,一個(gè)常用功能是能把查詢到的數(shù)據(jù)自動封裝起來,而不再需要我們操作ResultSet。

要想使用DBUtils,首先要導(dǎo)入包:commons-dbutils-1.4.jar

增、刪、改:

  • DbUtils的寫操作是一類,讀操作是一類
  • 寫操作主要是調(diào)用update函數(shù)

1.新建QueryRunner對象【如果傳入一個(gè)連接池對象,那么后續(xù)操作的數(shù)據(jù)庫連接就是這個(gè)連接池的連接;如果不設(shè)置,那么執(zhí)行update時(shí)要給一個(gè)連接對象】

2.調(diào)用update函數(shù).

update()有多個(gè)重構(gòu)函數(shù),可以依據(jù)情況來選擇使用:

如何使用Java中的JDBC

如何使用Java中的JDBC

如何使用Java中的JDBC

查:

  • 寫操作主要是調(diào)用query函數(shù)
  • 查詢操作的同時(shí),可以配合javabean把數(shù)據(jù)封裝起來(數(shù)據(jù)返回的數(shù)據(jù)在ResultSet中,傳入一個(gè)ResultSetHandler對象以操作ResultSet中的數(shù)據(jù))。
  • 如下圖所示,ResultSetHandler對象是必須的參數(shù),所以說,查出數(shù)據(jù)但不處理的操作不要使用DBUtils。

如何使用Java中的JDBC

自定義操作數(shù)據(jù):調(diào)用ResultSetHandler的匿名實(shí)現(xiàn)類中的handle方法處理resultset的數(shù)據(jù)

如何使用Java中的JDBC

手動封裝:調(diào)用ResultSetHandler的實(shí)現(xiàn)類中的handle方法來講resultset的數(shù)據(jù)封裝到對象中

如何使用Java中的JDBC

自動封裝數(shù)據(jù):根據(jù)傳入的ResultSetHandler對象來處理數(shù)據(jù)

如何使用Java中的JDBC

常見ResultSetHandler實(shí)現(xiàn)類:

  • BeanHandler :把數(shù)據(jù)庫中的一行數(shù)據(jù)根據(jù)變量名自動封裝到對象中;如果查詢語句返回多條結(jié)果,將ResultSet中第一行的數(shù)據(jù)根據(jù)變量名自動封裝到對象中
  • BeanListHandler:把數(shù)據(jù)庫中的多行數(shù)據(jù)根據(jù)變量名自動封裝到對象中,并存儲到List中返回。所以返回結(jié)果是一個(gè)含有多個(gè)bean對象的list
  • ScalarHandler :將ResultSet中一條記錄的某一列的數(shù)據(jù)存成Object,返回值是一個(gè)Object。不給參數(shù)時(shí)默認(rèn)是第一列的值,參數(shù)可以給列數(shù),也可以給字段名 【可以用于統(tǒng)計(jì)函數(shù)等返回一個(gè)值的情況】
  • ArrayHandler :把一條記錄的所有數(shù)據(jù)存儲到一個(gè)數(shù)組中,第一列的數(shù)據(jù)在數(shù)組的第一個(gè)位置。
  • ArrayListHandler:與ArrayHandler功能類似,但可以返回包含多個(gè)數(shù)組的list了。

補(bǔ)充:對于封裝成對象的,需要提供一個(gè)bean類.class參數(shù),這是為了能創(chuàng)建對象

關(guān)閉流、釋放資源:

DbUtils中提供了可以關(guān)閉各種資源的靜態(tài)方法

如何使用Java中的JDBC

如何使用Java中的JDBC

補(bǔ)充:

  • 由于DbUtils支持傳入一個(gè)Connection對象,所以在一些比如轉(zhuǎn)賬的事務(wù)管理中,若是加錢和減錢在不同函數(shù)中,DbUtils可以借助傳入同一個(gè)Connection對象來實(shí)現(xiàn)事務(wù)管理。

看完上述內(nèi)容,是不是對如何使用Java中的JDBC有進(jìn)一步的了解,如果還想學(xué)習(xí)更多內(nèi)容,歡迎關(guān)注億速云行業(yè)資訊頻道。

向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI