数据库连接池实现

目录

前提:如果我要操作多个表,那么就会产生冗余的JDBC步骤,另一个弊端就是每次都需要数据库连接对象(Connection),获取效率低下,每次使用时都需要先进行连接

数据库连接池的特点:

数据库连接池的好处:

自己实现连接池过程:

创建一个连接池类:

所以我们来自己写一个连接类:

实现前面逻辑,我们就可以创建一个连接池测试类:

利用druid德鲁伊连接池来实现连接池


前提:如果我要操作多个表,那么就会产生冗余的JDBC步骤,另一个弊端就是每次都需要数据库连接对象(Connection),获取效率低下,每次使用时都需要先进行连接

因此我们可以自己来实现一个数据库连接池,避免每次都需要来写Connection

数据库连接池的特点:

1.数据库连接池是一个容器,负责分配,管理数据库连接

2.它允许应用程序重复使用一个现有的数据库连接,而不是再重新建立一个

3.释放空闲时间超过最大空闲时间的数据库来避免因为没有释放数据库连接而引起的数据库连接泄露

数据库连接池的好处:

1.资源重用

2.提升系统响应速度

3.避免数据库连接遗漏:当其余使用者需要连接而没有链接时,连接池会去判断其余未归还连接的线程池在干什么,如果发现使用者使用完链接后一直不归还,连接池会强制断开连接,此时等待的使用者就可以使用了

对比图:

自己实现连接池过程:
创建一个连接池类:

利用单列模式,确保其他测试类只能获取连接池Pool,而不能new 创建新的连接池

package JDBC.d1102.连接池;import java.sql.Connection;
import java.util.ArrayList;
import java.util.List;public class Pools {private Pools() {}private static Pools pools = new Pools();List<MyConnection> list = new ArrayList<>();{for (int i = 0; i < 5; i++) {MyConnection myConnection = new MyConnection();
//            Connection connection = myConnection.getConnection();list.add(myConnection);}}public static Pools getInstance() {return pools;}public static void main(String[] args) {Pools instance = Pools.getInstance();System.out.println(instance.list.size());}}

因为Connection 为接口,所以不能new,Connection也不是函数式接口,所以也不能利用匿名内部类来实现,

所以我们来自己写一个连接类:
package JDBC.d1102.连接池;import java.sql.Connection;
import java.sql.DriverManager;public class MyConnection extends Connect {String url = "jdbc:mysql:///study?useSSL=false";String userName = "root";String password = "root";Connection connection = null;private boolean isUse = false;private void createConnection() {try {Class.forName("com.mysql.jdbc.Driver");connection = DriverManager.getConnection(url, userName, password);} catch (Exception e) {e.printStackTrace();}}public Connection getConnection() {createConnection();return connection;}public boolean isUsed() {if (!isUse) {isUse = true;return  false;}else{return isUse;}}public boolean free() {isUse = false;return true;}
}

创建一个 Connect 类来实现Connection连接类,使MyConnection 继承Connect,间接的实现实现Connection连接类,这样Connection类就可以调用MyConnection 中写的方法,用于判断,是否使用同一个连接,(用还是没用,还还是没还)

package JDBC.d1102.连接池;import java.sql.*;
import java.util.Map;
import java.util.Properties;
import java.util.concurrent.Executor;public class Connect implements Connection {@Overridepublic Statement createStatement() throws SQLException {return null;}@Overridepublic PreparedStatement prepareStatement(String sql) throws SQLException {return null;}@Overridepublic CallableStatement prepareCall(String sql) throws SQLException {return null;}@Overridepublic String nativeSQL(String sql) throws SQLException {return null;}@Overridepublic void setAutoCommit(boolean autoCommit) throws SQLException {}@Overridepublic boolean getAutoCommit() throws SQLException {return false;}@Overridepublic void commit() throws SQLException {}@Overridepublic void rollback() throws SQLException {}@Overridepublic void close() throws SQLException {}@Overridepublic boolean isClosed() throws SQLException {return false;}@Overridepublic DatabaseMetaData getMetaData() throws SQLException {return null;}@Overridepublic void setReadOnly(boolean readOnly) throws SQLException {}@Overridepublic boolean isReadOnly() throws SQLException {return false;}@Overridepublic void setCatalog(String catalog) throws SQLException {}@Overridepublic String getCatalog() throws SQLException {return null;}@Overridepublic void setTransactionIsolation(int level) throws SQLException {}@Overridepublic int getTransactionIsolation() throws SQLException {return 0;}@Overridepublic SQLWarning getWarnings() throws SQLException {return null;}@Overridepublic void clearWarnings() throws SQLException {}@Overridepublic Statement createStatement(int resultSetType, int resultSetConcurrency) throws SQLException {return null;}@Overridepublic PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency) throws SQLException {return null;}@Overridepublic CallableStatement prepareCall(String sql, int resultSetType, int resultSetConcurrency) throws SQLException {return null;}@Overridepublic Map<String, Class<?>> getTypeMap() throws SQLException {return null;}@Overridepublic void setTypeMap(Map<String, Class<?>> map) throws SQLException {}@Overridepublic void setHoldability(int holdability) throws SQLException {}@Overridepublic int getHoldability() throws SQLException {return 0;}@Overridepublic Savepoint setSavepoint() throws SQLException {return null;}@Overridepublic Savepoint setSavepoint(String name) throws SQLException {return null;}@Overridepublic void rollback(Savepoint savepoint) throws SQLException {}@Overridepublic void releaseSavepoint(Savepoint savepoint) throws SQLException {}@Overridepublic Statement createStatement(int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {return null;}@Overridepublic PreparedStatement prepareStatement(String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {return null;}@Overridepublic CallableStatement prepareCall(String sql, int resultSetType, int resultSetConcurrency, int resultSetHoldability) throws SQLException {return null;}@Overridepublic PreparedStatement prepareStatement(String sql, int autoGeneratedKeys) throws SQLException {return null;}@Overridepublic PreparedStatement prepareStatement(String sql, int[] columnIndexes) throws SQLException {return null;}@Overridepublic PreparedStatement prepareStatement(String sql, String[] columnNames) throws SQLException {return null;}@Overridepublic Clob createClob() throws SQLException {return null;}@Overridepublic Blob createBlob() throws SQLException {return null;}@Overridepublic NClob createNClob() throws SQLException {return null;}@Overridepublic SQLXML createSQLXML() throws SQLException {return null;}@Overridepublic boolean isValid(int timeout) throws SQLException {return false;}@Overridepublic void setClientInfo(String name, String value) throws SQLClientInfoException {}@Overridepublic void setClientInfo(Properties properties) throws SQLClientInfoException {}@Overridepublic String getClientInfo(String name) throws SQLException {return null;}@Overridepublic Properties getClientInfo() throws SQLException {return null;}@Overridepublic Array createArrayOf(String typeName, Object[] elements) throws SQLException {return null;}@Overridepublic Struct createStruct(String typeName, Object[] attributes) throws SQLException {return null;}@Overridepublic void setSchema(String schema) throws SQLException {}@Overridepublic String getSchema() throws SQLException {return null;}@Overridepublic void abort(Executor executor) throws SQLException {}@Overridepublic void setNetworkTimeout(Executor executor, int milliseconds) throws SQLException {}@Overridepublic int getNetworkTimeout() throws SQLException {return 0;}@Overridepublic <T> T unwrap(Class<T> iface) throws SQLException {return null;}@Overridepublic boolean isWrapperFor(Class<?> iface) throws SQLException {return false;}
}
实现前面逻辑,我们就可以创建一个连接池测试类:

如果一开始没有获取到连接,可以利用重试机制来再次获取,直到能够获取到连接或者重试获取不到连接池为止

package JDBC.d1102.连接池;import java.sql.Connection;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.List;public class ConnectionPoolTest {//public static void main(String[] args) {// 向t1表中插入一条数据Pools pools = Pools.getInstance();// 单例模式List<MyConnection> list = pools.list;Connection connection = null;MyConnection myConnection = null;int i = 1;while (i <= 10) {for (MyConnection conn : list) {// 此种情况代表我获取到了之前没有线程使用的链接,那么我可以用if (!conn.isUsed()) {connection =  conn.getConnection();myConnection =conn;}}if (connection == null) {try {Thread.sleep(10);} catch (InterruptedException e) {e.printStackTrace();}}i++;}Statement statement = null;try {if (connection == null) {System.out.println("太忙了,没有空闲的链接");} else {statement = connection.createStatement();String sql = "insert into t1 values(4,4,20)";int effectRows = statement.executeUpdate(sql);if (effectRows > 0) {System.out.println("插入成功");} else {System.out.println("插入失败");}myConnection.free();}} catch (SQLException e) {e.printStackTrace();} finally {if (statement != null) {try {statement.close();} catch (SQLException e) {e.printStackTrace();}}}}
}

利用druid德鲁伊连接池来实现连接池

 首先导入德鲁伊jar包

创建一个druid.properties配置类

driverClassName=com.mysql.jdbc.Driver
url=jdbc:mysql:///study?useSSL=false&useServerPrepStmts=true
username=root
password=root
# 初始化链接数量
initialSize=5
# 最大链接数量
maxActive=10
#最大等待时间ms
maxWait=3000

创建测试类:

package JDBC.d1102.text;import com.alibaba.druid.pool.DruidDataSourceFactory;import javax.sql.DataSource;
import java.io.FileInputStream;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Properties;public class druidText {public static void main(String[] args) {Statement statement = null;Connection connection = null;ResultSet resultSet = null;try {FileInputStream fileInputStream = new FileInputStream("src/JDBC/d1102/text/druid.properties");Properties properties = new Properties();properties.load(fileInputStream);DataSource dataSource = DruidDataSourceFactory.createDataSource(properties);connection= dataSource.getConnection();statement = connection.createStatement();String sql = "select * from student";resultSet = statement.executeQuery(sql);while (resultSet.next()) {int s_id = resultSet.getInt("s_id");String name = resultSet.getString("s_name");String s_brith = resultSet.getString("s_brith");String s_sex = resultSet.getString("s_sex");System.out.println(s_id + " " + name + " " + s_brith + " " + s_sex);}}catch (Exception e){e.printStackTrace();}finally {if (statement != null) {try {statement.close();} catch (SQLException e) {e.printStackTrace();}}if (connection != null) {try {connection.close();} catch (SQLException e) {e.printStackTrace();}}}}
}

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/58829.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

软件测试基础三(前端知识)

前端基础 1. HTML&#xff08;超文本标记语言&#xff09; 1.1. 基本概念 定义&#xff1a;HTML 是用来描述网页的一种语言&#xff0c;指的是超文本标记语言&#xff08;Hyper Text Markup Language&#xff09;。它不是编程语言&#xff0c;而是一种标记语言&#xff0c;由…

优化用于传感应用的衬底集成波导技术

ANSYS HFSS 是一款功能强大的电磁仿真软件&#xff0c;支持为微流体生物传感器应用设计和分析衬底集成波导 &#xff08;SIW&#xff09; 技术。它为快速设计优化、材料选择、系统集成和虚拟原型制作提供了一个强大的平台。借助 ANSYS HFSS&#xff0c;研究人员和工程师可以高效…

Linux 开机自动挂载硬盘

在日常使用 Linux 系统的过程中&#xff0c;我们可能需要挂载一些机械硬盘或者移动硬盘来存储数据。手动挂载虽然简单&#xff0c;但每次重启后都需要重新操作&#xff0c;未免有些繁琐。那么&#xff0c;如何让硬盘在开机时自动挂载呢&#xff1f;本篇博客将详细介绍如何通过配…

[项目] C++基于多设计模式下的同步异步日志系统

[项目] C基于多设计模式下的同步&异步日志系统 文章目录 [项目] C基于多设计模式下的同步&异步日志系统日志系统1、项目介绍2、开发环境3、核心技术4、日志系统介绍4.1 日志系统的价值4.2 日志系统技术实现4.2.1 同步写日志4.2.2 异步写日志 5、相关技术知识5.1 不定参…

[论文阅读] | 智能体长期记忆

更新记录&#xff1a; 2024.11.2 人大高瓴长期记忆综述 文章目录 人大高瓴长期记忆综述智能体与环境交互记忆的来源/形式/操作来源&#xff1a;(1)当前任务历史信息 (2)其他任务的信息 (3)外部知识形式&#xff1a;如何表达记忆的内容&#xff0c;通过(1)文本 (2)参数(训练到模…

Rust 力扣 - 59. 螺旋矩阵 II

文章目录 题目描述题解思路题解代码题目链接 题目描述 题解思路 使用一个全局变量current记录当前遍历到的元素的值 我们只需要一圈一圈的从外向内遍历矩阵&#xff0c;每一圈遍历顺序为上边、右边、下边、左边&#xff0c;每遍历完一个元素后current 我们需要注意的是如果上…

AppInventor2能否用网络摄像头画面作为屏幕的背景?

// 视频是否可以作为背景&#xff1f; // 有会员提问&#xff1a;能否用网络摄像头的实时画面作为屏幕的背景&#xff1f;就跟这个一样背景全覆盖&#xff1a; 摄像头画面是一个在线的网站链接视频流。 // 原先思路 // 1、目前原生组件无法直接实现这个功能&#xff0c;屏幕…

国产操作系统卖疯了!最营收7.84亿,最低1.5亿

最近看各种报道&#xff0c;似乎国产化有提速的绩效&#xff0c;那么既然如此&#xff0c;各个国产操作系统厂商是不是都起飞了呢&#xff1f; 周末闲暇之余&#xff0c;我们来看看各家的营收表现。 银河麒麟2024年1-9月一共卖了多少钱&#xff1f; 前几天中国软件发布了202…

CDN加速实战:使用七牛云CDN加速阿里云OSS资源访问

今天是双11搞活动,在阿里云1元注册了个域名,想着在学CDN,想使用CDN做个加速项目,但是阿里的要收费,上网查了下七牛云的不收费,想着将七牛云的CDN结合阿里的DNS做个访问加速,刚好看到了阿里的一个文章,照着改了改,实践成功了。 阿里文章:使用CDN加速OSS资源访问_对象…

嵌入式学习——IIC协议

IIC&#xff08;Inter-Integrated Circuit&#xff09;是一种串行通信协议&#xff0c;由飞利浦公司于1980年代提出。它允许多个从设备通过两条线&#xff08;SDA和SCL&#xff09;与一个或多个主设备进行通信。IIC协议是多主、多从的&#xff0c;适合在短距离内的设备间通信。…

qt QStatusBar详解

1、概述 QStatusBar是Qt框架提供的一个小部件&#xff0c;用于在应用程序窗口底部显示状态信息。它可以显示一些固定的文本和图标&#xff0c;并且可以通过API动态更新显示内容。QStatusBar通常是一个水平的窗口部件&#xff0c;能够显示多行文本内容&#xff0c;非常适合用于…

大型语言模型的运行成本分析

大型语言模型 (LLM) 一直处于生成式 AI 革命的前沿&#xff0c;尤其是自 ChatGPT 出现以来。然而&#xff0c;它们的全部潜力尚未得到释放&#xff0c;而一个重大障碍是成本。将 LLM 纳入应用程序的费用范围从按需用例的几美分到在云环境中托管单个 LLM 实例的每月 20,000 美元…

Matlab高光谱遥感

原文链接&#xff1a;Matlab高光谱遥感https://mp.weixin.qq.com/s?__bizMzUzNTczMDMxMg&mid2247623643&idx5&sne4557ed43728f851140b100f42286988&chksmfa8da23ccdfa2b2a4d795bf4087f672faaa7082d1f52e046616ab7bf196a6eef89ea553d06b1&token1392391660&…

OPENAI官方prompt文档解析

官方文档地址:https://platform.openai.com/docs/guides/gpt-best-practices 文档中文版来源:OpenAI 官方提示工程指南 [译] | 宝玉的分享 (baoyu.io) 1.写清楚说明 如果prompt给的范围十分模糊或是过于宽泛,那么GPT就会开始猜测您想要的内容,从而导致生成的结果偏离预期. …

共模噪声和差模噪声

电源芯片加上负载和不加负载输出的纹波不一样&#xff0c;不加负载的情况下纹波比较小。 可以测量出DCDC电源的输出电压纹波为100Khz&#xff0c;刚好对应电源芯片的开关频率。可以看到纹波上面有一部分的小噪声&#xff0c;放大后用示波器观察频率为几Mhz。 对付上面的频率比…

DevOps赋能:优化业务价值流的实战策略与路径(上)

上篇&#xff1a;价值流引领与可视化体系构建 一、前言 在快速迭代的软件项目和产品开发生态中&#xff0c;我们始终围绕两个核心目标&#xff1a;一是确保每一项工作都能为客户创造实际价值&#xff0c;这是产品团队的核心使命&#xff1b;二是确保这些有价值的工作能够高效…

机器学习之fetch_olivetti_faces人脸识别--基于Python实现

fetch_olivetti_faces 数据集下载 fetch_olivetti_faceshttps://github.com/jikechao/olivettifaces sklearn.datasets.fetch_olivetti_faces(*, data_homeNone, shuffleFalse, random_state0, download_if_missingTrue, return_X_yFalse, n_retries3, delay1.0)[source] L…

HTML 语法规范——代码注释、缩进与格式、标签与属性、字符编码等

文章目录 一、代码注释1.1 使用注释的主要目的1.2 使用建议二、标签的使用2.1 开始标签和结束标签2.2 自闭合标签2.3 标签的嵌套2.4 标签的有效性三、属性四、缩进与格式4.1 一致的缩进4.2 元素单独占用一行4.3 嵌套元素的缩进4.4 避免冗长的行五、字符编码六、小结在开发 HTML…

Charles简单压力测试

1.接口请求次数&#xff0c;并发量&#xff0c;请求延迟时间均可配置 1.1选中需要进行测试的接口&#xff0c;鼠标右键选中【repeat advance】 2.设置并发参数 下面的图中&#xff0c;选择了1个接口&#xff0c;每次迭代中1个接口同时请求&#xff0c;迭代1000次&#xff08;…

HrmonyOS 赋能套件介绍

文章为官方教程以及自己的部分理解&#xff0c;用于上下班的查看学习。官方视频教程地址&#xff1a;HarmonyOS应用开发者基础认证-华为开发者学堂 (huawei.com) HarmonOS 赋能套件全景 感知 通过白皮书了解认识 HarmonOS 应用开发的核心理念、关键能力和创新体验 学习与评估…