自己动手写个数据库连接池

本文介绍了一个简单的数据库连接池实现,通过复用Connection对象减少数据库访问的开销,提高应用程序性能。文章包括接口定义、连接池类实现及测试案例。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

说到数据库连接池也是初学者会望而却步,认为是如何高深莫测的东西,其实可以用一句话来解释: 连接池的出现是为了用户频繁访问数据库而造成速度和性能上的迟缓才对访问数据库的方法作了一点修改,这个修改就是把原本要关闭的Connection对象放到Collection集合里以重复利用。下面,我就来自己写一个数据库的连接池,看看他到底有多“神奇”(为了简单起见,以下代码都没有加导入包,读者可利用Eclipse的自动导入方式导入):

首先,我们先创建一个接口,此接口很简单,就是提供一个获得连接和一个关闭连接的方法:

public interface DBSource {
 public Connection getConnection()throws SQLException;
 public void closeConnection(Connection con)throws SQLException;

}

然后我们编写一个数据库连接池类实现DBSource 接口:

public class BasicDBSource implements DBSource {
 private Properties pro;//属性对象
 private String url;
 private String user;
 private String password;
 private int max;//最大连接数
 private List<Connection> connections;//集合类存放被关闭的Connection对象
 
 public BasicDBSource()throws IOException,ClassNotFoundException{
  this("myjdbc.properties");//调用带参的构造函数
 }
 
 public BasicDBSource(String configFile)throws IOException,ClassNotFoundException{

//获取属性文件,因为我将url,user,password,max,driver的属性值存放在一个myjdbc.properties的属性文件里

//这样设计的目的也是为了提高代码的低偶合度,为重构做些小小的贡献
  pro=new Properties();
  pro.load(new FileInputStream(configFile));
  url=pro.getProperty("url");
  user=pro.getProperty("user");
  password=pro.getProperty("password");
  max=Integer.parseInt(pro.getProperty("poolmax"));
  Class.forName(pro.getProperty("driver"));
  connections=new ArrayList<Connection>();
  
 }

 public synchronized void closeConnection(Connection con) throws SQLException {

//如果集合中的Connection对象个数大于等于允许的最大连接数,则关闭连接

//否则,将要关闭的Connection对象放入集合栈中,等需要连接时再弹出
  if (connections.size()>=max) {
   con.close();
  } else {
   connections.add(con);

  }
  

 }

 public synchronized Connection getConnection() throws SQLException {

//要获取连接时,先判断集合栈中是否存有压入的Connection对象,如果没有,则像原来一样创建连接

//如果有,则弹出集合栈中的Connection对象,无需再行连接
  if (connections.size()==0) {
   return DriverManager.getConnection(url,user,password);
  } else {
   int last=connections.size()-1;
   return connections.remove(last);

  }
  
 }

}

最后,我们写一个测试类,来测试一下结果:

public class ConnectionPoolDemo {

 public static void main(String[] args) {
  try {
   DBSource dbsource=new BasicDBSource();
   Connection con1=dbsource.getConnection();
   dbsource.closeConnection(con1);
   Connection con2=dbsource.getConnection();
   dbsource.closeConnection(con2);
   System.out.println(con1==con2);
   
  } catch (IOException e) {
   e.printStackTrace();
  }
  catch (ClassNotFoundException e) {
   e.printStackTrace();
  }
  catch (SQLException e) {
   e.printStackTrace();
  }
  
  

 }

}
测试结果为:true

也就是说con1对象和con2对象是同一个对象,说明在连接数据库时是将集合中的连接对象赋予请求连接的对象(集合非空),而不用每次访问都先去连接数据库。

以上的实例只是为了让大家明白数据库连接池的原理,当然在网上有许多优秀的连接池原码可以拿来就用,大家也可以参考一下。

 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值