数据库连接池

2022-06-21 00:00:00 数据库 连接池

1、什么是数据库连接池?

数据库连接池负责分配、管理和释放数据库连接,它允许应用程序重复使用一个现有的数据库连接,而不是再重新建立一个;

释放空闲时间超过最大空闲时间的数据库连接来避免因为没有释放数据库连接而引起的数据库连接遗漏。

这项技术能明显提高对数据库操作的性能

2、连接池解决的问题???

      不断的创建、销毁链接,会导致访问数据库服务器的压力,而且对于内存来说,不断的开辟与销毁,内存的使用率极低。使用数据库连接池可以明显提高对数据库操作的性能!

      数据库连接池的解决方案是在应用程序启动时建立足够的数据库连接,并将这些连接组成一个连接池(简单说:在一个“池”里放了好多半成品的数据库连接对象),由应用程序动态地对池中的连接进行申请、使用和释放。对于多于连接池中连接数的并发请求,应该在请求队列中排队等待并且应用程序可以根据池中连接的使用率,动态增加或减少池中的连接数

3、数据库连接池的工作原理???

  1、三步骤     连接池的建立,连接池中连接的使用管理,连接池的关闭

一、连接池的建立:创建几个连接对象,以便使用的时候能从连接池中获取

二、客户请求数据库连接时,首先查看连接池中是否有空闲连接,若存在,将连接分配给用户使用;如果没有空闲连接,则查看当前所开的连接数是否已经达到最大的连接数,如果没有达到,就重新创建一个连接给请求的客户,如果达到就按照设定的最大等待时间进行等待,超出的最大等待的时间,就抛出异常给用户,当用户释放数据连接的时候,先判断该连接的引用次数是否超过了规定的值,如果超过就删除,如果没有的话,就保留为其他客户服务。保证了数据库连接的有效复用,避免频繁的建立、释放连接所带来的系统资源的资源开销。

三、连接池的关闭,当应用程序退出的时候i,关闭所有的连接,释放相关的资源,正好与创建相反

4、数据库连接配置时的参数(可选,有默认值)

最小连接数:是连接池一直保持的数据库连接,所以如果应用程序对数据库连接的使用量不大,将会有大量的数据库连接资源被浪费.

最大连接数:是连接池能申请的最大连接数,如果数据库连接请求超过次数,后面的数据库连接请求将被加入到等待队列中,这会影响以后的数据库操作

最大空闲时间:连接池对象最长的闲置时间,如果长时间没有被使用,那么此连接对象就会被销毁。

获取连接超时时间:池子中总共有50条连接,当这50条连接都处于工作状态时,第51个连接请求到达,让其加入到等待队列中,等待时间如果超过了设置的超时时间,则抛出异常

初始化连接数:当数据库连接池创建时,初始化的连接数量

5、主流的数据库连接池技术

创建QueryRunner时,可以传递一个数据源DataSource,我们可以将这个数据源理解为数据库连接池,那么我们现在使用不同的数据库连接池技术,目的就只有一个,得到数据源对象

6、DBCP

介绍:DBCP(DataBase Connection Pool)属于Apache顶级项目Commons中的核心子项目(最早在Jakarta Commons里就有),它内部依赖于Commons中的另一个子项目Pool,连接池最核心的“池”,就是由Pool组件提供的,因此,DBCP的性能实际上就是Pool的性能

步骤:

导包 build path

书写dbcp.properties属性文件,文件目录在src下

书写dbcp工具类,来提供数据源

测试数据源是否可用

《数据库连接池》

7、封装一个工具类,专门用于向外界提供dbcp的数据源。

/**
 * 此类的作用就是生成并且提供dbcp的数据源
 * @author Administrator
 *
 */
public class DBCPUtils {
	private static DataSource dataSource = null;
	
	//完成对数据源的赋值,赋值只需要走一次,所以在静态代码块中完成赋值
	static {
		Properties properties = new Properties();
		FileInputStream fStream = null;
		try {
			//创建输入流对象,来读取配置文件dbcp.properties
			fStream = new FileInputStream("src/dbcp.properties");
			//将流中读取到的内容加载属性文件对象中
			properties.load(fStream);
			//将加载完毕内容的属性文件对象传递到dbcp创建数据源的方法中,生成数据源
			dataSource = BasicDataSourceFactory.createDataSource(properties);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	//返回数据源的方法
	public static DataSource getDataSource() {
		return dataSource;
	}
}

测试代码的书写:

public static void main(String[] args) throws SQLException {
		/*
		 	使用dbcp数据源来操作数据库
		 	方式1:在创建QueryRunner对象,给定数据源,此时不需要书写连接获取的代码,会自动从给定的数据源中获取连接
		 	使用完毕,不需要执行关闭资源的方法,连接对象会自动归还池子
		 	
		 	方式2:我们可以通过数据源的getConnection()获取到由池子管理的数据库连接对象
		 	使用完毕后,执行关闭资源的方法,并不是将连接对象销毁,而是将连接对象归还池子
		 */
		/*
		QueryRunner qRunner = new QueryRunner(DBCPUtils.getDataSource());
		List<User> users = qRunner.query("select * from user", 
				new BeanListHandler<User>(User.class));
		for (User user : users) {
			System.out.println(user);
		}*/
		
		DataSource dataSource = DBCPUtils.getDataSource();
		Connection connection = dataSource.getConnection();
		QueryRunner qRunner = new QueryRunner();
		List<User> users = qRunner.query(connection, "select * from user", 
				new BeanListHandler<User>(User.class));
		for (User user : users) {
			System.out.println(user);
		}
		DbUtils.close(connection);
	}

写一个参数文件dbcp.properties:

//创建输入流对象,来读取配置文件dbcp.properties

7、druid的使用

介绍:它除了提供性能卓越的连接池功能外,还集成了SQL监控,黑名单拦截等功能,用它自己的话说,Druid是“为监控而生”。借助于阿里这个平台的号召力,产品一经发布就赢得了大批用户的拥趸,从用户使用的反馈来看,Druid也确实没让用户失望。

使用步骤:

导包   《数据库连接池》

书写配置文件druid.properties    《数据库连接池》

书写druid工具类,来生成并提供druid的数据源   

/**
 * 此类专门用于生成druid数据源
 * @author Administrator
 *
 */
public class DruidUtils {
	//声明数据源
	private static DataSource dataSource = null;
	
	//为数据源赋值
	static {
		Properties properties = new Properties();
		FileInputStream fStream = null;
		try {
			fStream = new FileInputStream("src/druid.properties");
			properties.load(fStream);
			dataSource = DruidDataSourceFactory.createDataSource(properties);
		} catch (Exception e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} finally {
			try {
				if (fStream != null) {
					fStream.close();
				}
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}
	}
	
	//返回获取数据源的方法
	public static DataSource getDataSource() {
		return dataSource;
	}
}

书写测试代码

public static void main(String[] args) {
		//使用druid+dbutils完成添加操作
		QueryRunner qRunner = new QueryRunner(DruidUtils.getDataSource());
		try {
			int row = qRunner.update("insert into user values (null, ?, ?, ?)", 
								"小阔爱", "666", "男");
			System.out.println(row > 0 ? "添加成功" : "添加失败");
		} catch (SQLException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}

8、c3p0的使用

介绍:C3P0是我使用的第一款数据库连接池,在很长一段时间内,它一直是Java领域内数据库连接池的代名词,当年盛极一时的Hibernate都将其作为内置的数据库连接池,可以业内对它的稳定性还是认可的。C3P0功能简单易用,稳定性好这是它的优点,但是性能上的缺点却让它彻底被打入冷宫。C3P0的性能很差,差到即便是同时代的产品相比它也是垫底的,更不用和Druid、HikariCP等相比了。正常来讲,有问题很正常,改就是了,但c3p0最致命的问题就是架构设计过于复杂,让重构变成了一项不可能完成的任务。随着国内互联网大潮的涌起,性能有硬伤的c3p0彻底的退出了历史舞台。

使用步骤:

导包   《数据库连接池》

书写c3p0.properties文件,一定要放在src下   《数据库连接池》

如果c3p0的配置文件名称叫c3p0.properties,并且放在了src下,那么就会自动读取配置文件!

测试代码  

测试代码:
public class C3P0Demo {
	private static ComboPooledDataSource dataSource = new ComboPooledDataSource();
	
	public static void main(String[] args) {
		QueryRunner qRunner = new QueryRunner(dataSource);
		try {
			User user = qRunner.query("select * from user where uid = ?",
					new BeanHandler<User>(User.class), 2);
			System.out.println(user);
		} catch (SQLException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();

五,duid,dbcp,c3p0 的区别。

《数据库连接池》

 

 

 

 

 

 

 

    原文作者:chen983234416
    原文地址: https://blog.csdn.net/chen983234416/article/details/102689351
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。

相关文章