從JDBC鏈接到C3P0數據庫鏈接池
在Java開發中,使用JDBC操做數據庫的四個步驟以下:java
①加載數據庫驅動程序(Class.forName("數據庫驅動類");)
②鏈接數據庫(Connection con = DriverManager.getConnection();)
③操做數據庫(PreparedStatement stat = con.prepareStatement(sql);stat.executeQuery();)
④關閉數據庫,釋放鏈接(con.close();)
②鏈接數據庫(Connection con = DriverManager.getConnection();)
③操做數據庫(PreparedStatement stat = con.prepareStatement(sql);stat.executeQuery();)
④關閉數據庫,釋放鏈接(con.close();)
也就是說,全部的用戶都須要通過此四步進行操做,可是這四步之中有三步(①加載數據庫驅動程序、②鏈接數據庫、④關閉數據庫,釋放鏈接)對全部人都是同樣的,而全部人只有在操做數據庫上是不同,那麼這就形成了性能的損耗。
那麼最好的作法是,準備出一個空間,此空間裏專門保存着所有的數據庫鏈接,之後用戶用數據庫操做的時候不用再從新加載驅動、鏈接數據庫之類的,而直接今後空間中取走鏈接,關閉的時候直接把鏈接放回到此空間之中。
那麼此空間就能夠稱爲鏈接池(保存全部的數據庫鏈接)
什麼是鏈接池:
鏈接池是建立和管理一個鏈接的緩衝池的技術,這些鏈接準備好被任何須要它們的線程使用;簡單理解爲,當一輛汽車搬運東西,若是使用jdbc鏈接,(jdbc鏈接:與數據庫創建鏈接、發送操做數據庫的語句並處理結果)那麼每一次都要去打開數據庫,得到鏈接,關閉數據庫。假設汽車搬運的東西是鏈接,那麼我可不能夠每一次將鏈接搬運多個呢?而不是jdbc那樣,一次只搬運一個鏈接,而後就把汽車扔掉?這時候,使用鏈接池。
原理:
鏈接池基本的思想是在系統初始化的時候,將數據庫鏈接做爲對象存儲在內存中,當用戶須要訪問數據庫時,並不是創建一個新的鏈接,而是從鏈接池中取出一個已創建的空閒鏈接對象。使用完畢後,用戶也並不是將鏈接關閉,而是將鏈接放回鏈接池中,以供下一個請求訪問使用。而鏈接的創建、斷開都由鏈接池自身來管理。同時,還能夠經過設置鏈接池的參數來控制鏈接池中的初始鏈接數、鏈接的上下限數以及每一個鏈接的最大使用次數、最大空閒時間等等。也能夠經過其自身的管理機制來監視數據庫鏈接的數量、使用狀況等。 爲何要用到鏈接池 數據庫鏈接池的基本思想就是爲數據庫鏈接創建一個「緩衝池」。預先在緩衝池中放入必定數量的鏈接,當須要創建數據庫鏈接時,只需從「緩衝池」中取出一個,使用完畢以後再放回去。咱們能夠經過設定鏈接池最大鏈接數來防止系統無盡的與數據庫鏈接。鏈接池主要由三部分組成:鏈接池的創建、鏈接池中鏈接的使用管理、鏈接池的關閉。數據庫鏈接池的最小鏈接數和最大鏈接數的設置要考慮到如下幾個因素:
- 最小鏈接數:是鏈接池一直保持的數據庫鏈接,因此若是應用程序對數據庫鏈接的使用量不大,將會有大量的數據庫鏈接資源被浪費.
- 最大鏈接數:是鏈接池能申請的最大鏈接數,若是數據庫鏈接請求超過次數,後面的數據庫鏈接請求將被加入到等待隊列中,這會影響之後的數據庫操做
- 若是最小鏈接數與最大鏈接數相差很大:那麼最早鏈接請求將會獲利,以後超過最小鏈接數量的鏈接請求等價於創建一個新的數據庫鏈接.不過,這些大於最小鏈接數的數據庫鏈接在使用完不會立刻被釋放,他將被放到鏈接池中等待重複使用或是空間超時後被釋放
下面這是c3p0數據庫鏈接池的運行機制 mysql
(1) 程序初始化時建立鏈接池
(2) 使用時向鏈接池申請可用鏈接
(3) 使用完畢,將鏈接返還給鏈接池
(4) 程序退出時,斷開全部鏈接,並釋放資源sql
我用的開發工具是IDEA,建立的是Maven項目,要使用c3p0須要配置相關模塊,如圖所示數據庫
<!-- mysql驅動--> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> <version>5.0.5</version> </dependency> <!-- c3p0 --> <dependency> <groupId>com.mchange</groupId> <artifactId>c3p0</artifactId> <version>0.9.5.2</version> </dependency>
db.properties 文件名不能改, 必須放在src下 ,配置文件中的key名稱不能變工具
好,完成這些後開始鏈接數據庫性能
package jdbc; import com.mchange.v2.c3p0.ComboPooledDataSource; import java.beans.PropertyVetoException; import java.io.FileInputStream; import java.io.IOException; import java.sql.Connection; import java.sql.PreparedStatement; import java.sql.ResultSet; import java.sql.SQLException; import java.util.Properties; public class JDBCUtils { public void setConnection() throws SQLException, PropertyVetoException, IOException { //建立鏈接池 ComboPooledDataSource dataSource = new ComboPooledDataSource(); //加載配置文件 Properties properties = new Properties(); properties.load(new FileInputStream("src/main/java/db.properties")); String driver = properties.getProperty("driver"); String url = properties.getProperty("url"); String username = properties.getProperty("username"); String password = properties.getProperty("password"); //得到鏈接 Connection conn = null; PreparedStatement ps = null; ResultSet res = null; dataSource.setDriverClass(driver); dataSource.setJdbcUrl(url); dataSource.setUser(username); dataSource.setPassword(password); conn = dataSource.getConnection(); String sql = "select * from user"; ps = conn.prepareStatement(sql); res = ps.executeQuery(); while (res.next()){ System.out.println(res.getInt("id")+" "+res.getString("username")+" "+res.getString("password")); } } } class text{ public static void main(String[] args) throws PropertyVetoException, SQLException, IOException { JDBCUtils jdbcUtils = new JDBCUtils(); jdbcUtils.setConnection(); } }
本文同步分享在 博客"泰斗賢若如"(CNBlog)。
若有侵權,請聯繫 support@oschina.cn 刪除。
本文參與「OSC源創計劃」,歡迎正在閱讀的你也加入,一塊兒分享。開發工具