<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    Chinese To English     英文 轉 中文             
             
    隨筆-27  評論-53  文章-0  trackbacks-0

            大家都知道,在實際應用開發中都會用到數據庫。要用數據庫我們就必須和數據取得連接,否則一切都是空談,我想這個沒有什么好多說的。正因如此問題就出來了,和數據庫取得連接是比較耗資源,而一個網站每天的訪問量也是驚人的,想一想如果客戶端每向服務器發送一個請求服器就要進行打開連接和關閉連接的工作,這樣做明顯是不合理,在實際開發中如果是這樣去實現數據的持久化真是不可思議。所以引入了連接池的概念,所謂連接池就是當用完一個連接后不是將連接直接關閉而是將它放入到一個容器中緩存放起來,下次再用的時候就直接在容器中取,從而初實現連接的重用。

    1:連接池實現類

      1package net.vicp.jiasoft.dpcp.connectionpool;
      2
      3import java.sql.Connection;
      4import java.sql.DriverManager;
      5import java.sql.SQLException;
      6import java.util.Vector;
      7import net.vicp.jiasoft.dpcp.dynaproxy.ConnectionProxy;
      8import net.vicp.jiasoft.dpcp.util.PropertiesUtil;
      9
     10/**
     11 * @author Jak.Shen
     12 * 日期:2008-3-31
     13 * 說明:連接池實現類
     14 */

     15
     16public class ConnectionPool {
     17
     18    private static ConnectionPool connectionPool;//自身靜態成員變量,用于實現單例.
     19    private static Vector connPool;//連接緩存容器
     20    private int poolMaxSize = 10;//連接池最大緩存數
     21    private String userName;//連接用戶名
     22    private String password;//連接密碼
     23    private String driverClass;//連接驅動
     24    private String url;//連接字符串
     25
     26    /**
     27     * 私有構造方法,初始化變量.并心預填充連接池。
     28     */

     29    private ConnectionPool() {
     30        String temp = PropertiesUtil.getValueByKey("poolMaxSize");
     31        if (temp != null{
     32            poolMaxSize = Integer.parseInt(temp);
     33        }

     34        userName = PropertiesUtil.getValueByKey("userName");
     35        password = PropertiesUtil.getValueByKey("password");
     36        driverClass = PropertiesUtil.getValueByKey("driverClass");
     37        url = PropertiesUtil.getValueByKey("url");
     38        connPool = new Vector();
     39        int size = 0;
     40        if (poolMaxSize > 5{
     41            size = 5;
     42        }
     else {
     43            size = poolMaxSize;
     44        }

     45        for (int i = 0; i < size; i++{
     46            connPool.add(createConnection());//預填充連接池
     47        }

     48    }

     49
     50    /**
     51     * 此方法用于創建并返回連接池對象。
     52     * @return
     53     */

     54    public static ConnectionPool newInstance() {
     55        if (connectionPool == null{
     56            connectionPool = new ConnectionPool();
     57        }

     58        return connectionPool;
     59    }

     60
     61    /**
     62     * 此方法用于創建一個連接。
     63     * @return
     64     */

     65    private Connection createConnection() {
     66        Connection connection = null;
     67        try {
     68            Class.forName(driverClass);
     69        }
     catch (ClassNotFoundException e) {
     70            e.printStackTrace();
     71        }

     72        try {
     73            connection = DriverManager.getConnection(url, userName, password);
     74        }
     catch (SQLException e) {
     75            e.printStackTrace();
     76        }

     77        return connection;
     78    }

     79
     80    /**
     81     * 此方法用于將用完的連接放入池中。
     82     */

     83    public static synchronized void releaseConnection(Connection connection) {
     84        connPool.add(connection);
     85    }

     86
     87    /**
     88     * 此方法用于返回一個連接。
     89     * @return
     90     */

     91    public synchronized Connection getConnection() {
     92        // 要防止直接關閉連接因此需要對Connection的close()方法進行攔截
     93        // 所以需要要給Connection接口動態加入代理,getConnection()是加入代理的好地方法
     94        // connectionProxy是動態代理對象
     95        ConnectionProxy connectionProxy = new ConnectionProxy();
     96        int size = connPool.size();
     97        if (connPool.size() == 0 || size < poolMaxSize) {
     98            connectionProxy.setConnection(createConnection());
     99            return connectionProxy.proxyBind();
    100        }

    101        Connection connection = (Connection) connPool.get(size - 1);
    102        connectionProxy.setConnection(connection);
    103        connPool.remove(size - 1);
    104        return connectionProxy.proxyBind();
    105    }

    106}

    107

    2:動態代理類
     1package net.vicp.jiasoft.dpcp.dynaproxy;
     2
     3import java.lang.reflect.InvocationHandler;
     4import java.lang.reflect.Method;
     5import java.lang.reflect.Proxy;
     6import java.sql.Connection;
     7import net.vicp.jiasoft.dpcp.connectionpool.ConnectionPool;
     8
     9/** 
    10 * @author Jak.Shen
    11 * 日期:2008-3-31
    12 * 說明:動態代理實類,實現InvocationHandler接口就可以成為動態代理了.要注意的是只能對接口代理。
    13 */

    14 
    15public class ConnectionProxy implements InvocationHandler {
    16
    17    private Connection connection;//動態代理的對象
    18
    19    public ConnectionProxy() {
    20    }

    21
    22    public ConnectionProxy(Connection connection) {
    23        this.connection = connection;
    24    }

    25
    26    /**
    27     * 重寫實現InvocationHandler方法invoke()。
    28     * 此處注意@Override標注在JDK1.6中才支持,JDK1.6以下版本請將@Override標注去掉。
    29     */

    30    @Override
    31    public Object invoke(Object proxy, Method method, Object[] args)
    32            throws Throwable {
    33        // 如果方法是close(),就替換成連接池的releaseConnection()方法.
    34        if (method.getName().equals("close")) {
    35            System.out.println("before invoke !");
    36            ConnectionPool.releaseConnection(connection);
    37            System.out.println("after invoke !");
    38        }
     else {
    39            // 對非close()方法,不做處理,直接調用.
    40            return method.invoke(connection, args);
    41        }

    42        return null;
    43    }

    44
    45    /**
    46     * 綁定要進行代理的對象
    47     * @return
    48     */

    49    public Connection proxyBind() {
    50        // 返回一個指定接口的代理類實例
    51        // newProxyInstance() arg0-->定義代理類的類加載器
    52        // newProxyInstance() arg1-->代理類要實現的接口列表
    53        // newProxyInstance() arg2-->指派方法調用的調用處理程序(此處就是去調用this對象的invoke())
    54        Connection proxyConnection = (Connection) Proxy.newProxyInstance(
    55                connection.getClass().getClassLoader(), connection.getClass()
    56                        .getInterfaces(), this);
    57        return proxyConnection;
    58    }

    59
    60    public Connection getConnection() {
    61        return connection;
    62    }

    63
    64    public void setConnection(Connection connection) {
    65        this.connection = connection;
    66    }

    67}

    68

    3:屬性文件操作工具類
     1package net.vicp.jiasoft.dpcp.util;
     2
     3import java.io.FileInputStream;
     4import java.io.FileNotFoundException;
     5import java.io.IOException;
     6import java.util.Properties;
     7
     8/** 
     9 * @author Jak.Shen
    10 * 日期:2008-3-31
    11 * 說明:屬性文件操作工具類
    12 */

    13
    14public class PropertiesUtil {
    15    private static Properties properties = new Properties();
    16    private static FileInputStream fileInputStream;
    17
    18    /**
    19     * 從屬性文件中根據Key取值
    20     * @param key
    21     * @return
    22     */

    23    public static String getValueByKey(String key) {
    24        if (fileInputStream == null{
    25            try {
    26                fileInputStream = new FileInputStream("src/dpcp.properties");
    27            }
     catch (FileNotFoundException e) {
    28                e.printStackTrace();
    29            }

    30        }

    31        try {
    32            properties.load(fileInputStream);
    33        }
     catch (IOException e) {
    34            e.printStackTrace();
    35        }

    36        return properties.get(key).toString();
    37    }

    38}

    39

    4:測試客戶端
     1package net.vicp.jiasoft.dpcp.client;
     2
     3import java.sql.Connection;
     4import java.sql.SQLException;
     5import net.vicp.jiasoft.dpcp.connectionpool.ConnectionPool;
     6
     7/** 
     8 * @author Jak.Shen
     9 * 日期:2008-3-31
    10 * 說明:動態代理連接池測試客戶端
    11 */

    12public class DbPoolClient {
    13
    14    public static void main(String[] args) {
    15        ConnectionPool connectionPool = ConnectionPool.newInstance();
    16        Connection connection = connectionPool.getConnection();
    17        try {
    18            connection.close();
    19        }
     catch (SQLException e) {
    20            e.printStackTrace();
    21        }

    22    }

    23}

    24

    5:屬性配置文件(dpcp.properties)
     1#最大連接數
     2poolMaxSize=4
     3#連接用戶名
     4userName=scott
     5#連接密碼
     6password=tiger
     7#連接驅動
     8driverClass=oracle.jdbc.driver.OracleDriver
     9#連接字符串
    10url=jdbc:oracle:thin:@localhost:1521:ACCP

    源碼下載 -- (ConnectionPool.rar)

    杰森 
    郵箱:json.shen(at)gmail.com
    網站:www.shenjia.org
    posted on 2008-03-31 18:17 杰森 閱讀(2440) 評論(2)  編輯  收藏 所屬分類: JavaSE

    評論:
    # re: Java實現簡單動態代理連接池 2008-04-18 10:33 | YangYang
    寫的很好,學習了。 msn:seeblue1981@hotmail.com  回復  更多評論
      
    # re: Java實現簡單動態代理連接池 2008-04-18 16:53 | Jak.Shen
    @YangYang
    多謝支持!  回復  更多評論
      
    嗨117
    主站蜘蛛池模板: 亚洲日韩在线中文字幕第一页| 国产亚洲免费的视频看| 国产精品福利片免费看| 久久精品国产亚洲AV电影| 成年女人18级毛片毛片免费 | 亚洲综合图色40p| 97人妻无码一区二区精品免费| 亚洲AV性色在线观看| 亚洲国产成人片在线观看| 最近最新MV在线观看免费高清| 日本永久免费a∨在线视频 | 国内成人精品亚洲日本语音| 国产AV无码专区亚洲A∨毛片| 四虎永久在线精品免费网址| 久久免费观看视频| 亚洲欧美黑人猛交群| 亚洲AV综合色一区二区三区| 国产成人在线观看免费网站 | 久久精品亚洲综合| 国产又大又黑又粗免费视频 | 国产中文在线亚洲精品官网| 成年免费大片黄在线观看岛国| h片在线观看免费| 亚洲av永久无码天堂网| 中文字幕亚洲综合久久2| 免费播放美女一级毛片 | 一级看片免费视频| 亚洲国产最大av| 亚洲国产精品自在线一区二区| 亚洲午夜爱爱香蕉片| 日本免费一二区在线电影| 免费能直接在线观看黄的视频| 日本道免费精品一区二区| 美女18毛片免费视频| 亚洲 日韩经典 中文字幕| 老汉色老汉首页a亚洲| 综合亚洲伊人午夜网 | 成年女人A毛片免费视频| 国产成人综合久久精品亚洲| 亚洲av专区无码观看精品天堂| 亚洲av无码一区二区三区不卡 |