1. 程式人生 > >執行緒池c3p0例項

執行緒池c3p0例項

1.maven需要引入兩個包

<dependency>
  <groupId>mysql</groupId>
  <artifactId>mysql-connector-java</artifactId>
  <version>5.1.42</version>
</dependency>
<dependency>
  <groupId>com.mchange</groupId>
  <artifactId>c3p0</artifactId>
  <version>0.9.5.2</version>
</dependency>

 

 2.建立配置檔案c3p0-config.xml(1.名字必須為這個,系統會自動載入,可以自定義配置資訊,也可以用預設的配置資訊.2.當通過設定配置檔案xml時它可以自動查詢,不用通過類載入的方式了。只要它的檔案路徑是在classloader(類路徑也可以說是classes下面)的路徑下面。(在官方文件中可以找到配置檔案))

<?xml version="1.0" encoding="UTF-8"?>
<c3p0-config>
    <!--預設配置-->
    <default-config>
        <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>

    <!--配置連線池mysql-->
    <named-config name="mysql">
        <property name="driverClass">com.mysql.jdbc.Driver</property>
        <property name="jdbcUrl">jdbc:mysql://localhost:3306/news2</property>
        <property name="user">root</property>
        <property name="password">123456</property>
        <property name="initialPoolSize">10</property>   <!--連線池初始化時建立的連線數,default : 3-->
        <property name="maxIdleTime">30</property>   <!--最大空閒時間,超過空閒時間的連線將被丟棄。為0或負數則永不丟棄。預設為0 單位 s-->
        <property name="maxPoolSize">100</property>   <!--連線池中保留的最大連線數。預設為15-->
        <property name="minPoolSize">10</property>   <!--連線池中保留的最小連線數。預設為15-->
    </named-config>

    <!--
			1.最常用配置

			initialPoolSize:連線池初始化時建立的連線數,default : 3(建議使用)

			minPoolSize:連線池保持的最小連線數,default : 3(建議使用)

			maxPoolSize:連線池中擁有的最大連線數,如果獲得新連線時會使連線總數超過這個值則不會再獲取新連線,而是等待其他連線釋放,所以這個值有可能會設計地很大,default : 15(建議使用)

			acquireIncrement:連線池在無空閒連線可用時一次性建立的新資料庫連線數,default : 3(建議使用)



			2.管理連線池的大小和連線的生存時間

			maxConnectionAge:配置連線的生存時間,超過這個時間的連線將由連線池自動斷開丟棄掉。當然正在使用的連線不會馬上斷開,而是等待它close再斷開。配置為0的時候則不會對連線的生存時間進行限制。default : 0 單位 s(不建議使用)

			maxIdleTime:連線的最大空閒時間,如果超過這個時間,某個資料庫連線還沒有被使用,則會斷開掉這個連線。如果為0,則永遠不會斷開連線,即回收此連線。default : 0 單位 s(建議使用)

			maxIdleTimeExcessConnection.s:這個配置主要是為了快速減輕連線池的負載,比如連線池中連線數因為某次資料訪問高峰導致建立了很多資料連線,但是後面的時間段需要的資料庫連線數很少,需要快速釋放,必須小於maxIdleTime。其實這個沒必要配置,maxIdleTime已經配置了。default : 0 單位 s(不建議使用)



			3.配置連線測試:

			automaticTestTable:配置一個表名,連線池根據這個表名用自己的測試sql語句在這個空表上測試資料庫連線,這個表只能由c3p0來使用,使用者不能操作。default : null(不建議使用)

			preferredTestQuery:與上面的automaticTestTable二者只能選一。自己實現一條SQL檢測語句。default : null(建議使用)

			idleConnectionTestPeriod:用來配置測試空閒連線的間隔時間。測試方式還是上面的兩種之一,可以用來解決MySQL8小時斷開連線的問題。因為它保證連線池會每隔一定時間對空閒連線進行一次測試,從而保證有效的空閒連線能每隔一定時間訪問一次資料庫,將於MySQL8小時無會話的狀態打破。為0則不測試。default : 0(建議使用)

			testConnectionOnCheckin:如果為true,則在close的時候測試連線的有效性。default : false(不建議使用)

			testConnectionOnCheckout:效能消耗大。如果為true,在每次getConnection的時候都會測試,為了提高效能,儘量不要用。default : false(不建議使用)



			4.配置PreparedStatement快取:

			maxStatements:連線池為資料來源快取的PreparedStatement的總數。由於PreparedStatement屬於單個Connection,所以這個數量應該根據應用中平均連線數乘以每個連線的平均PreparedStatement來計算。同時maxStatementsPerConnection的配置無效。default : 0(不建議使用)

			maxStatementsPerConnection:連線池為資料來源單個Connection快取的PreparedStatement數,這個配置比maxStatements更有意義,因為它快取的服務物件是單個數據連線,如果設定的好,肯定是可以提高效能的。為0的時候不快取。default : 0(看情況而論)



			5.重連相關配置

			acquireRetryAttempts:連線池在獲得新連線失敗時重試的次數,如果小於等於0則無限重試直至連接獲得成功。default : 30(建議使用)

			acquireRetryDelay:連線池在獲得新連線時的間隔時間。default : 1000 單位ms(建議使用)

			breakAfterAcquireFailure:如果為true,則當連接獲取失敗時自動關閉資料來源,除非重新啟動應用程式。所以一般不用。default : false(不建議使用)

			checkoutTimeout:配置當連線池所有連線用完時應用程式getConnection的等待時間。為0則無限等待直至有其他連線釋放或者建立新的連線,不為0則當時間到的時候如果仍沒有獲得連線,則會丟擲SQLException。其實就是acquireRetryAttempts*acquireRetryDelay。default : 0(與上面兩個,有重複,選擇其中兩個都行)



			6.定製管理Connection的生命週期

			connectionCustomizerClassName:用來定製Connection的管理,比如在Connection acquire 的時候設定Connection的隔離級別,或者在Connection丟棄的時候進行資源關閉,

			就可以通過繼承一個AbstractConnectionCustomizer來實現相關方法,配置的時候使用全類名。有點類似監聽器的作用。default : null(不建議使用)



			7.配置未提交的事務處理

			autoCommitOnClose:連線池在回收資料庫連線時是否自動提交事務。如果為false,則會回滾未提交的事務,如果為true,則會自動提交事務。default : false(不建議使用)

			forceIgnoreUnresolvedTransactions:這個配置強烈不建議為true。default : false(不建議使用)

			一般來說事務當然由自己關閉了,為什麼要讓連線池來處理這種不細心問題呢?



			8.配置debug和回收Connection

			unreturnedConnectionTimeout:為0的時候要求所有的Connection在應用程式中必須關閉。如果不為0,則強制在設定的時間到達後回收Connection,所以必須小心設定,保證在回收之前所有資料庫操作都能夠完成。這種限制減少Connection未關閉情況的不是很適用。建議手動關閉。default : 0 單位 s(不建議使用)

			debugUnreturnedConnectionStackTraces:如果為true並且unreturnedConnectionTimeout設為大於0的值,當所有被getConnection出去的連線unreturnedConnectionTimeout時間到的時候,就會打印出堆疊資訊。只能在debug模式下適用,因為列印堆疊資訊會減慢getConnection的速度default : false(不建議使用)



			其他配置項:因為有些配置項幾乎沒有自己配置的必要,使用預設值就好,所以沒有再寫出來。




-->
    ......
    <!--配置連線池3-->
    ......
    <!--配置連線池4-->
    ......
</c3p0-config>

3.測試用例測試c3p0:

import java.beans.PropertyVetoException;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

import org.junit.Test;

import com.mchange.v2.c3p0.ComboPooledDataSource;
public class C3p0Test2{

    //使用編碼方式實現c3p0資料庫連線池
    @Test
    public void TestXml() throws PropertyVetoException, SQLException{
        ComboPooledDataSource dataSource=new ComboPooledDataSource("mysql");
        Connection con=dataSource.getConnection();
        String sql="select * from user ";
        PreparedStatement ps=con.prepareStatement(sql);
        ResultSet rs=ps.executeQuery();
        List<User> list=new ArrayList<User>();
        while(rs.next()){
            User user=new User();
            user.setUserId(rs.getInt("userId"));
            user.setName(rs.getString("name"));
            user.setPassword(rs.getString("password"));
            user.setEmail(rs.getString("email"));
            user.setSalt(rs.getString("salt"));
            user.setHeadIconUrl(rs.getString("headIconUrl"));
            list.add(user);
        }
        for(User user:list)
        System.out.println(user.getName());

    }

}

 結果: