自己用Java编写的连接池

论坛 期权论坛 编程之家     
选择匿名的用户   2021-6-2 19:15   903   0

参考网上各方面的资料,自己编写了一个连接池,不过连接池存在一些问题,希望大神们指点,不多说了,直接在代码上有注释:

package com.tyxh.mypool;

import java.io.IOException;
import java.io.InputStream;
import java.sql.Connection;
import java.util.Properties;
import java.util.Vector;

public class DBConnectFactory {
 private static DBConnectFactory factory = null; 
 
 private static final int INIT_SIZE = 2; //连接池初始化大小
 
 private static final int MAX_SIZE = 10; //连接池的最大值
 
 private String driver;

 private String url;

 private String username;

 private String password;
 
 private long activeTime = 5000;
 
 private Vector<DBConnection> connectPool = null;//存放数据库连接的向量
 
 public DBConnectFactory() {
  //初始化连接的配置
  this.initProperties();
  //初始化数据库的连接池
  this.initPool();
 }
 
 private void initProperties() {
  Properties dbPro = new Properties();
  InputStream input = this.getClass().getResourceAsStream("db.properties");
  try {
   dbPro.load(input);
   this.driver = dbPro.getProperty("driver");
   this.url = dbPro.getProperty("url");
   this.username = dbPro.getProperty("username");
   this.password = dbPro.getProperty("password");
   
  } catch (IOException e) {
   e.printStackTrace();
  }
 }
 
 private void initPool() {
  if(null == connectPool) {
   //创建数据库连接池
   connectPool = new Vector<DBConnection>(INIT_SIZE);
   //循环创建数据库连接
   for (int i = 0; i < INIT_SIZE; i++) {
    DBConnection db = new DBConnection(driver, url, username, password);
    System.out.println("创建了DBConnection连接");
    connectPool.add(db);
   }
  }
 }
 
 public static synchronized DBConnectFactory getDBConnectFactory() {
  if(null == factory) {
   factory = new DBConnectFactory();
  }
  return factory;
 }
 
 public DBConnection createNewConectionTimer() {
  //此方法的作用是:当获取连接的时候,如果连接不够了,才会执行这个方法创建连接
  synchronized (connectPool) {
   DBConnection db = new DBConnectionTimer(driver, url, username, password, activeTime);
   System.out.println("创建了DBConnectionTimer连接");
   connectPool.add(db);
   return db;
  }
 }
 
 public Connection getConnection() {
  System.out.println("此时连接池中还有的连接数: " + connectPool.size());
  synchronized (connectPool) {
   Connection conn = null;
   DBConnection db = null;
   while(true) {
    //循环查找空闲的连接,直到找到位置
    for (int i = 0; i < connectPool.size(); i++) {
     db = connectPool.get(i);
     if(!db.isUsed()) {
      System.out.println("有空闲的连接");
      //此连接处于空闲状态
      if(db instanceof DBConnectionTimer) {
       System.out.println("取得的链接是DBConnectionTimer");
       //如果db是DBConnectionTimer对象
       DBConnectionTimer dbTimer = (DBConnectionTimer)db;
       dbTimer.cacel(); //取消定时
       conn = db.getConn();
       db.setUsed(true); //设置此链接繁忙状态
       return conn;
      } else {
       System.out.println("取得的连接是DBConnection");
       //如果db是DBConnection对象
       conn = db.getConn();
       db.setUsed(true); //设置此链接繁忙状态
       return conn;
      }
     }
     
    }
    System.out.println("没有空闲的连接");
    //如果没有找到空闲的连接,则创建连接
    if(null == conn && connectPool.size() < this.MAX_SIZE) {
     //如果连接池的大小小于要求的最大连接数,才可以创建
     db = this.createNewConectionTimer();
     conn = db.getConn();
     db.setUsed(false);//新创建的连接设置为空闲状态
     return conn;
    }
    
    //如果连接池的大小达到了最大连接数
    if(null == conn && connectPool.size() == this.MAX_SIZE) {
     System.out.println("连接池满了");
     try {
      //进行等待,知道有链接进入空闲状态
      connectPool.wait();
     } catch (InterruptedException e) {
      e.printStackTrace();
     }
    }
    
   }
  }
 }
 
 public void releaseConnection(Connection conn) {
  synchronized (connectPool) {
   for (int i = 0; i < connectPool.size(); i++) {
    DBConnection db = connectPool.get(i);
    if(db instanceof DBConnectionTimer) {
     DBConnectionTimer dbTimer = (DBConnectionTimer) db;
     DBConTimerTask task = new DBConTimerTask(connectPool, dbTimer);
     dbTimer.tick(task);
     System.out.println("释放了DBConnectionTimer的对象");
    }else {
     //固定的连接,一直存在
     if(conn == db.getConn()) {
      db.setUsed(false);
      connectPool.notify();
      System.out.println("释放了DBConnection的对象");
      break;
     }
    }
    
   }
  }
 }
 
}

package com.tyxh.mypool;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;

public class DBConnection {
 private String driver;
 private String url;
 private String username;
 private String password;
 private boolean isUsed;
 private Connection conn;
 
 public DBConnection(String driver,String url,String username,String password){
  this.driver = driver;
  this.url = url;
  this.username = username;
  this.password = password;
  this.isUsed = false;
  //创建数据库连接
  this.createConnection();
 }

 private void createConnection() {
  try {
   Class.forName(this.driver);
   conn = DriverManager.getConnection(url, username, password);
  } catch (ClassNotFoundException e) {
   e.printStackTrace();
  } catch (SQLException e) {
   e.printStackTrace();
  }
  
 }
 
 public String getDriver() {
  return driver;
 }

 public void setDriver(String driver) {
  this.driver = driver;
 }

 public String getUrl() {
  return url;
 }

 public void setUrl(String url) {
  this.url = url;
 }

 public String getUsername() {
  return username;
 }

 public void setUsername(String username) {
  this.username = username;
 }

 public String getPassword() {
  return password;
 }

 public void setPassword(String password) {
  this.password = password;
 }

 public boolean isUsed() {
  return isUsed;
 }

 public void setUsed(boolean isUsed) {
  this.isUsed = isUsed;
 }

 public Connection getConn() {
  return conn;
 }

 public void setConn(Connection conn) {
  this.conn = conn;
 }
 
}

package com.tyxh.mypool;

import java.util.Timer;

public class DBConnectionTimer extends DBConnection {

 private long activeTime;
 private Timer timer;
 
 public DBConnectionTimer(String driver, String url, String username,
   String password, long activeTime) {
  super(driver, url, username, password);
  this.activeTime = activeTime;
  timer = new Timer();
 }
 
 public void tick(DBConTimerTask task) {
  try{
   this.timer.schedule(task, activeTime);
   System.out.println("定时开始");
  } catch(IllegalStateException e) {
//   e.printStackTrace();
   System.err.println("已经存在task了");
  }
  
 }
 
 public void cacel(){
  this.timer.cancel();
  System.out.println("取消定时");
 }
 
}

package com.tyxh.mypool;

import java.sql.SQLException;
import java.util.TimerTask;
import java.util.Vector;

public class DBConTimerTask extends TimerTask {

 private Vector<DBConnection> connectPool = null;
 private DBConnectionTimer dbTimer;
 
 public DBConTimerTask(Vector<DBConnection> connectPool,
   DBConnectionTimer dbTimer) {
  super();
  this.connectPool = connectPool;
  this.dbTimer = dbTimer;
 }


 @Override
 public void run() {
  //将过期的数据库连接移除
  try {
   dbTimer.getConn().close();
  } catch (SQLException e) {
   e.printStackTrace();
  }
  connectPool.remove(dbTimer);
  System.out.println("移除超出生命周期的数据库连接!");
 }
 
}

package com.tyxh.mypool;

import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;

public class MulTest extends Thread {

 @Override
 public void run() {
  DBConnectFactory factory = DBConnectFactory.getDBConnectFactory();
  Connection conn = factory.getConnection();
  try {
   Statement state = conn.createStatement();
   String sql = "select count(*) from employees";
   ResultSet rs = state.executeQuery(sql);
   while(rs.next()){
    System.out.println(rs.getInt(1));
   }
  } catch (SQLException e) {
   e.printStackTrace();
  } finally {
   factory.releaseConnection(conn);
  }
   
 }
 
}

package com.tyxh.mypool;

import java.sql.Connection;

public class MainTest {

 public static void main(String[] args) {
  MulTest mul1 = new MulTest();
  mul1.start();
  MulTest mul2 = new MulTest();
  mul2.start();
  MulTest mul3 = new MulTest();
  mul3.start();
  MulTest mul4 = new MulTest();
  mul4.start();
  MulTest mul5 = new MulTest();
  mul5.start();
  MulTest mul6 = new MulTest();
  mul6.start();
  MulTest mul7 = new MulTest();
  mul7.start();
  MulTest mul8 = new MulTest();
  mul8.start();
  MulTest mul9 = new MulTest();
  mul9.start();
  MulTest mul10 = new MulTest();
  mul10.start();
  MulTest mul11 = new MulTest();
  mul11.start();
  MulTest mul12 = new MulTest();
  mul12.start();
 }

}

#db.properties     
#this properties is for database connect

driver=oracle.jdbc.driver.OracleDriver
url=jdbc:oracle:thin:@localhost:1521:XE
username=hr
password=hr


分享到 :
0 人收藏
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

积分:3875789
帖子:775174
精华:0
期权论坛 期权论坛
发布
内容

下载期权论坛手机APP