想必你們對這個應該已經比較熟悉了吧,數據庫鏈接池在數據庫鏈接上起着不可替代的做用,若是你處理的數據十分巨大的話,那就更顯重要了,java
如下是一個比較簡單的鏈接池實現(複雜鏈接池能夠查看c3p0的源代碼)mysql
1.數據庫鏈接信息接口:sql
package xidian.xidian.sl.dbconnectpool; /** * 數據庫鏈接信息接口 * 說明:將驅動、鏈接、數據庫名、數據庫密碼等數據鏈接基礎信息作成接口 * */ public interface IDataBase { /** * @return 數據庫驅動名 * 注意必須加入數據庫驅動包 * */ public String getDirver(); /** * @return 數據庫鏈接 * */ public String getConnUrl(); /** * @return 數據庫用戶名 * */ public String getUserName(); /** * @return 數據庫密碼 * */ public String getPassword(); }
2.數據庫鏈接信息接口實現類數據庫
package xidian.xidian.sl.dbconnectpool; /** * 數據庫鏈接信息接口實現類 * @author SeDion * 該類的默認驅動爲mysql-connector-java 5.0以上版本 * */ public class Mysql implements IDataBase { private String connurl; private String userName; private String password; public Mysql(String connurl,String userName,String password){ this.connurl = connurl; this.userName = userName; this.password = password; } public Mysql(String serverName,String dbName,String userName,String password){ this.connurl = "jdbc:mysql:"+serverName+"/"+dbName; this.userName = userName; this.password = password; } public String getConnUrl() { // TODO Auto-generated method stub return connurl; } public String getDirver() { // TODO Auto-generated method stub return "com.mysql.jdbc.Driver"; } public String getPassword() { // TODO Auto-generated method stub return password; } public String getUserName() { // TODO Auto-generated method stub return userName; } }
3.數據庫鏈接類安全
package xidian.xidian.sl.dbconnectpool; import java.sql.Connection; import java.sql.DriverManager; /** * 數據庫鏈接類 * 說明:該方法爲單個數據庫的鏈接類,能夠脫離鏈接池來單獨使用 * */ public class DBConnector { private IDataBase db; private Connection conn; private boolean free = true; public DBConnector(IDataBase db) { this.db = db; } /** * 鏈接數據庫 * @return 是否鏈接成功 */ public Connection connect() { try { Class.forName(db.getDirver()).newInstance(); conn = DriverManager.getConnection(db.getConnUrl(), db .getUserName(), db.getPassword()); System.out.println("connect success!"); } catch (Exception e) { System.out.println("connect failure!"); e.printStackTrace(); conn = null; } return conn; } public Connection getConnection(){ return conn; } /** * 判斷鏈接是否在使用 * 注意:在這個地方使用的是包訪問權限,這一項是特意爲鏈接池設置的,對於外面應用 的類並不能讀到此方法。 * */ boolean isFree() { return free; } /** * 設置鏈接是否空閒 * @param isFree * */ void setIsFree(boolean isFree) { this.free = isFree; } /** * 關閉數據庫 * @return 數據庫是否關閉成功 * */ public boolean close() { try { if (conn != null) { conn.close(); } return true; } catch (Exception e) { e.printStackTrace(); System.err.println("close failure!"); return false; } } /** * 釋放鏈接,爲鏈接池的重寫提供接口 * @return * */ boolean release(){ throw new RuntimeException("do not use the connection pool,can not release."); } }
4.數據庫鏈接池ide
package xidian.xidian.sl.dbconnectpool; import java.util.ArrayList; import java.util.List; /** * 鏈接池 * */ public class DBConnectPool { private int iniSize = 2; //鏈接池的初始大小 private int addSize = 2; //每次增長的大小 private int maxSize = 4; //最大的大小 private IDataBase db; private List<DBConnector> connections = null; //鏈接池,初始爲空 public DBConnectPool(IDataBase db){ this.db = db; iniPool(); } /** * 初始化鏈接池 */ public void iniPool(){ connections = new ArrayList<DBConnector>(); connections.addAll(addPool(iniSize)); } /** * 增長鏈接數 * @param size 要增長的數目 * @return * */ public List<DBConnector> addPool(int size){ List<DBConnector> subList = new ArrayList<DBConnector>(); for(int i=0; i<size; i++){ DBConnector conn = new DBPoolConnector(db); conn.connect(); subList.add(conn); } return subList; } /** * 判斷鏈接數是否超過鏈接池的最大鏈接數 * @return 是 否 * */ public boolean isOverRange(){ return connections.size() >= maxSize; } /** * 得到空閒鏈接 * @return 鏈接 * */ public DBConnector getConnection(){ //循環,有空閒鏈接則進行返回 for(DBConnector conn : connections){ if(conn.isFree()){ conn.setIsFree(false); return conn; } } //沒有空閒的 if(isOverRange()) { throw new RuntimeException("The connection number is over range."); }else{ int size = addSize; if((connections.size()+size) > maxSize){ size = maxSize - connections.size(); } List<DBConnector> subPool= addPool(size); connections.addAll(subPool); return subPool.get(0); } } /** * 設置鏈接爲空閒狀態 * @param conn * */ public void freeConnection(DBConnector conn){ conn.setIsFree(true); } /** * 釋放全部的空閒鏈接 * */ public void releaseAllFree(){ List<DBConnector> subPool = new ArrayList<DBConnector>(); for(DBConnector conn:connections){ if(conn.isFree()){ subPool.add(conn); conn.close(); } } connections.removeAll(subPool); } /** * 釋放鏈接 * @param conn 要釋放的鏈接 * */ public void release(DBConnector conn){ conn.release(); connections.remove(conn); } /** * 釋放全部鏈接 * */ public void release(){ for(DBConnector conn:connections) { conn.release(); } connections.removeAll(connections); } /** * 設置初始化最大鏈接數 * @param iniSize * */ public void setIniSize(int iniSize) { this.iniSize = iniSize; } /** * 設置每次遞增的最大數目 * @param addSize * */ public void setAddSize(int addSize) { this.addSize = addSize; } /** * 設置鏈接池的最大數目 * @param maxSize * */ public void setMaxSize(int maxSize) { this.maxSize = maxSize; } /** * 鏈接池內部類,用於管理DBConnector安全性,屏蔽close功能 * */ class DBPoolConnector extends DBConnector{ public DBPoolConnector(IDataBase db) { super(db); } @Override boolean release(){ return super.close(); } @Override public boolean close(){ throw new RuntimeException("Can not close,please use the Connection Pool close this connection."); } } }