当前位置: 首页 > news >正文

JAVA保姆式JDBC数据库免费教程之02-连接池技术

连接池

连接池概念

​ 概念:其实就是一个容器(集合),存放数据库连接的容器。

当系统初始化好后,容器被创建,容器中会申请一些连接对象,当用户来访问数据库时,从容器中获取连接对象,用户访问完之后,会将连接对象归还给容器。
在这里插入图片描述

缺点:用户每次请求都需要向数据库获得链接,而数据库创建连接通常需要消耗相对较大的资源,创建时间也较长。假设网站一天10万访问量,数据库服务器就需要创建10万次连接,极大的浪费数据库的资源,并且极易造成数据库服务器内存溢出。

连接池技术的核心思想是:连接复用,通过建立一个数据库连接池以及一套连接使用、分配、管理策略,使得该连接池中的连接可以得到高效、安全的复用,避免了数据库连接频繁建立、关闭的开销。

在这里插入图片描述

连接池好处

	1. 节约资源	2. 减少连接db的次数	3. 用户访问高效

连接池实现

1. 标准接口:DataSource   javax.sql包下的
1. 方法:* 获取连接:getConnection()* 归还连接:Connection.close()。如果连接对象Connection是从连接池中获取的,那么调用Connection.close()方法,则不会再关闭连接了。而是归还连接。

厂商实现

一般我们不去实现它,有数据库厂商来实现DBCP 1. C3P0:数据库连接池技术2. Druid:数据库连接池实现技术,由阿里巴巴提供的

c3p0数据库连接池

实现步骤

1. 导入jar包  c3p0-0.9.5.2.jar 
新建web项目 C3p0Test
使用c3p0的连接池,导入jar包
导入 mysql驱动包2. 定义配置文件:
名称: c3p0.properties 或者 c3p0-config.xml  
路径:直接将文件放在src目录下即可。3. 创建核心对象 数据库连接池对象 ComboPooledDataSource4. 获取连接: getConnection
代码:
//1.创建数据库连接池对象
DataSource ds  = new ComboPooledDataSource();
//2. 获取连接对象
Connection conn = ds.getConnection();

工具类的抽取

package cn.yanqi.utils;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import com.mchange.v2.c3p0.ComboPooledDataSource;// 你抽出的代码要有一定意义,并且要有通用性,任何一个关于这个工具类都 可以去使
public class JdbcUtils {//默认加载src 下面c3p0-config.xml加载private static ComboPooledDataSource ds = new ComboPooledDataSource();//创建连接public static Connection getConnection() throws SQLException{return ds.getConnection();}
}

配置文件

c3p0-config.xml 注意一定放在src下

<?xml version="1.0" encoding="UTF-8"?>
<c3p0-config><!-- 我们希望在配置文件中,出现链接的参数信息 --><default-config><!-- name 属性定义 链接参数的key 标签的内容 代表值--><property name="driverClass">com.mysql.jdbc.Driver</property><property name="jdbcUrl">jdbc:mysql:///day03</property><property name="user">root</property><property name="password">root</property><!-- 连接池参数 --><property name="initialPoolSize">5</property><property name="maxPoolSize">10</property><property name="checkoutTimeout">3000</property></default-config>
</c3p0-config>

测试

@Test
public void test1() throws SQLException {//封装的c3p0相关代码Connection conn = JdbcUtil.getConnection();Statement stmt = conn.createStatement();int i = stmt.executeUpdate("delete from user where id = 29");System.out.println(i);}

Druid数据库连接池

Druid数据库连接池实现技术 (德鲁伊),由阿里巴巴提供的

实现步骤

一、步骤:1. 导入jar包 druid-1.0.9.jar2. 定义配置文件:是xx.properties形式的可以叫任意名称,可以放在任意目录下, 一般都放在src3. 加载配置文件。Properties4. 获取数据库连接池对象:通过工厂来来获取  DruidDataSourceFactory5. 获取连接:getConnection代码实现://3.加载配置文件Properties pro = new Properties();InputStream is = 		       DruidDemo.class.getClassLoader().getResourceAsStream("druid.properties");pro.load(is);//4.获取连接池对象DataSource ds = DruidDataSourceFactory.createDataSource(pro);//5.获取连接Connection conn = ds.getConnection();
二、定义工具类1. 定义一个类 JDBCUtils2. 提供静态代码块加载配置文件,初始化连接池对象3. 提供方法1. 获取连接方法:通过数据库连接池获取连接2. 释放资源3. 获取连接池的方法

配置文件

在src中创建 druid.properties

    driverClassName=com.mysql.jdbc.Driverurl=jdbc:mysql:///db3username=rootpassword=root# 初始化连接数量initialSize=5# 最大连接数maxActive=10# 最大等待时间maxWait=3000

工具类的抽取

import java.io.IOException;
import java.sql.ResultSet;
import java.sql.SQLException;
/*** Druid连接池的工具类*/
public class JDBCUtils {//1.定义成员变量 DataSourceprivate static DataSource ds ;static{try {//1.加载配置文件Properties pro = new Properties();pro.load(JDBCUtils.class.getClassLoader().getResourceAsStream("druid.properties"));//2.获取DataSourceds = DruidDataSourceFactory.createDataSource(pro);} catch (IOException e) {e.printStackTrace();} catch (Exception e) {e.printStackTrace();}}/*** 获取连接*/public static Connection getConnection() throws SQLException {return ds.getConnection();}/*** 获取DataSource对象 (用于jdbcTemplate获取)*/public static DataSource getDataSource(){return ds;}
}

测试

public class DruidTest {@Testpublic void test(){Connection conn = DruidUtil.getConnection();try {Statement stmt = conn.createStatement();int i = stmt.executeUpdate("INSERT INTO `test`.`t_user`(`id`, `username`, `passworld`, `age`) VALUES (null, '江一燕', '520', 18)");System.out.println(i);} catch (SQLException e) {e.printStackTrace();}}
}

JDBCTemplate模版

概述

Spring JDBC Spring框架对JDBC的简单封装。提供了一个JDBCTemplate对象简化JDBC的开发(后面我们专门讲spring框架

实现步骤

1. 导入jar包 4 + 12. 创建JdbcTemplate对象。依赖于数据源DataSourceJdbcTemplate template = new JdbcTemplate(ds);3. 调用JdbcTemplate的方法来完成CRUD的操作update():执行DML语句。增、删、改语句queryForMap():查询结果将结果集封装为map集合,将列名作为key,将值作为value 将这条记录封装为一个map集合注意:这个方法查询的结果集长度只能是1queryForList():查询结果将结果集封装为list集合注意:将每一条记录封装为一个Map集合,再将Map集合装载到List集合中query():查询结果,将结果封装为JavaBean对象query的参数:RowMapper一般我们使用BeanPropertyRowMapper实现类。可以完成数据到JavaBean的自动封装new BeanPropertyRowMapper<类型>(类型.class)queryForObject:查询结果,将结果封装为对象一般用于聚合函数的查询

快速入门

/*** JdbcTemplate入门*/
public class JdbcTemplateDemo1 {public static void main(String[] args) {//1.导入jar包//2.创建JDBCTemplate对象JdbcTemplate template = new JdbcTemplate(JDBCUtils.getDataSource());//3.调用方法String sql = "update account set balance = 5000 where id = ?";int count = template.update(sql, 3);//insert update delete	System.out.println(count);//自已关闭,自已归还}
}

CRUD的测试

代码实现

数据库准备

CREATE TABLE `emp` (`id` int(11) NOT NULL AUTO_INCREMENT,`username` varchar(25) DEFAULT NULL,`job` varchar(100) DEFAULT NULL,`addr` varchar(25) DEFAULT NULL,PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;INSERT INTO `test`.`emp`(`id`, `username`, `job`, `addr`) VALUES (1, 'tom', '开发', '上海');
INSERT INTO `test`.`emp`(`id`, `username`, `job`, `addr`) VALUES (2, 'mary', '测试', '郑州');

实体类

// 注意事项:java属性名   要与   数据库的字段名保持一致,不然无法封装
public class Emp {private Integer id;private String username;private String job;private String addr;//提供有参无对构造方法//提供get  set 方法//提供toString方法
}

测试类

public class Test1 {//获取数据源private DataSource dataSource = JDBCUtil.getDataSource();//使用jdbcTemplate 技术,简化jdbc操作private JdbcTemplate JdbcTemplate = new JdbcTemplate(dataSource);//修改@Testpublic void testUpdateById(){String sql ="update emp set job = '财务' where id = ? ";int i = this.JdbcTemplate.update(sql, 2);System.out.println(i);}//添加@Testpublic void testAdd(){String sql ="insert into emp (id , username , job ,addr) values(?,?,?,?)";int i = JdbcTemplate.update(sql, null, "yiyan", "小秘", "郑州");System.out.println(i);}//删除@Testpublic void testDeleteById(){String sql ="delete from emp where id = ?";int i = JdbcTemplate.update(sql, 1);System.out.println(i);}//查询数据返回list@Testpublic void testQueryById(){String sql ="select * from emp where id = ?";//返回的是listList<Emp> emps = this.JdbcTemplate.query(sql, new BeanPropertyRowMapper<>(Emp.class), 2);for(Emp e : emps){System.out.println(e);}}//查询条数@Testpublic void testForObject(){String sql = "select count(1) from emp";Long i = this.JdbcTemplate.queryForObject(sql, Long.class);System.out.println(i);}//查询数据返回map@Testpublic void testQuery2(){String sql = "select * from emp where id = ?";//返回mapMap<String, Object> map = this.JdbcTemplate.queryForMap(sql,2);//map遍历Set<String> set = map.keySet();for(String key : set){Object o = map.get(key);System.out.println(key+" : "+o);}}/*** 查询数据返回对象中* 注意事项: 返回的单个对象必须要有结果,这个结果只能接受一条*           */public  Emp queryTest3(){Emp emp = null;try {String sql = "select * from emp where id = ?";//如果这里查到数据,就直接返回return this.template.queryForObject(sql, new BeanPropertyRowMapper<>(Emp.class),9);} catch (DataAccessException e) {//没有查询到,方式一// throw new RuntimeException("没有查询到数据!");//没有查询到,方式二return null;}}//测试 查询数据返回对象中public static void main(String[] args) {JdbcTemplateDemo jt = new JdbcTemplateDemo();Emp emp = jt.queryTest3();System.out.println(emp);}}

<>(Emp.class),9);
} catch (DataAccessException e) {
//没有查询到,方式一
// throw new RuntimeException(“没有查询到数据!”);
//没有查询到,方式二
return null;
}
}
//测试 查询数据返回对象中
public static void main(String[] args) {
JdbcTemplateDemo jt = new JdbcTemplateDemo();
Emp emp = jt.queryTest3();
System.out.println(emp);
}

}


相关文章:

JAVA保姆式JDBC数据库免费教程之02-连接池技术

连接池 连接池概念 ​ 概念&#xff1a;其实就是一个容器(集合)&#xff0c;存放数据库连接的容器。 当系统初始化好后&#xff0c;容器被创建&#xff0c;容器中会申请一些连接对象&#xff0c;当用户来访问数据库时&#xff0c;从容器中获取连接对象&#xff0c;用户访问完…...

视频片段怎么做成gif图?快试试这2种方法

动态gif图片作为当下非常常用的表情包&#xff0c;其丰富的内容生动的画面深受大众喜爱。那么&#xff0c;当我们想要将电影或是电视剧中的某一片段做成gif动态图片的时候&#xff0c;要如何操作呢&#xff1f;接下来&#xff0c;给大家分享两招视频转化gif的小窍门–使用【GIF…...

2.20计算机如何工作

一.计算机组成1.冯诺依曼体系CPU 中央处理器: 进行算术运算和逻辑判断.存储器: 分为外存和内存, 用于存储数据(使用二进制方式存储)输入设备: 用户给计算机发号施令的设备.输出设备: 计算机个用户汇报结果的设备内存和外存的区别(面试)访问速度:内存快,外存慢存储空间:内存小,外…...

[golang gin框架] 5.Cookie以及Session

1.Cookie(1).介绍HTTP 是无状态协议,简单地说&#xff0c;当浏览了一个页面&#xff0c;然后转到同一个网站的另一个页面&#xff0c;服务器无法认识到这是同一个浏览器在访问同一个网站,每一次的访问&#xff0c;都是没有任何关系的,如果要实现多个页面之间共享数据的话就可以…...

【牛客刷题专栏】0x0B:JZ3 数组中重复的数字(C语言编程题)

前言 个人推荐在牛客网刷题(点击可以跳转)&#xff0c;它登陆后会保存刷题记录进度&#xff0c;重新登录时写过的题目代码不会丢失。个人刷题练习系列专栏&#xff1a;个人CSDN牛客刷题专栏。 题目来自&#xff1a;牛客/题库 / 在线编程 / 剑指offer&#xff1a; 目录前言问题…...

js中的隐式类型转换有哪些

目录一、隐式类型转换条件二、 的隐式类型转换三、 的隐式类型转换四、object 的隐式类型转换探讨 object 的隐式转换执行顺序探讨 Symbol.toPrimitive 属性如何将对象转换为原始值在前端js这门动态弱类型语言中&#xff0c;不仅存在着显示类型转换&#xff0c;还存在许多隐式类…...

WuThreat身份安全云-TVD每日漏洞情报-2023-02-17

漏洞名称:IBM Aspera Faspex 预身份验证 RCE 漏洞 漏洞级别:高危 漏洞编号:CVE-2022-47986 相关涉及:IBM Aspera Faspex 漏洞状态:POC 参考链接:https://tvd.wuthreat.com/#/listDetail?TVD_IDTVD-2023-02805 漏洞名称:Kardex Mlog MCC PATH 遍历 漏洞级别:严重 漏洞编号:CVE…...

掌握MySQL分库分表(三)水平分库分表常见策略range、hash

文章目录range策略Range策略延伸基于Range范围分库分表业务场景hash取模案例规则水平分库分表&#xff0c;根据什么规则进行划分&#xff1f; range策略 自增id&#xff0c;根据ID范围进行分表&#xff08;左闭右开&#xff09; 规则案例&#xff1a; 1~1,000,000 是 table…...

CTFer成长之路之CTF中的SQL注入

CTF中的SQL注入CTF SQL注入 SQL注入-1 题目描述: 暂无 docker-compose.yml version: 3.2services:web:image: registry.cn-hangzhou.aliyuncs.com/n1book/web-sql-1:latestports:- 80:80启动方式 docker-compose up -d 题目Flag n1book{union_select_is_so_cool} Wri…...

python snap7读写PLC

主要在DB块里操作 读DB块 import snap7 import structdef plc_connection():PLC_IP 192.168.10.10PLC snap7.client.Client()PLC.connect(PLC_IP, rack0, slot1)return PLCPLC plc_connection()PLC.read_area()方法从PLC中读取指定区域的数据。 1200表示DB块的编号&#x…...

使用物联网进行智能能源管理的10大优势

如今&#xff0c;物联网推动了许多行业的自动化流程和运营效率&#xff0c;而物联网在能源领域的应用尤其受到消费者、企业甚至政府的关注。除了对电力供应链的诸多好处之外&#xff0c;物联网能源管理系统还让位于新的智能电网&#xff0c;并有望实现更高的安全性和效率。基于…...

工业4.0和工业物联网如何协同工作

虽然许多公司已经接受了工业物联网&#xff0c;但他们现在必须接受工业4.0对数据驱动的数字化转型的承诺。随着制造业、能源、公用事业和供应链应用迅速采用工业物联网(IIoT)&#xff0c;这些行业的新现实正在形成。工业物联网提供了企业管理数千个活动部件所需的数据类型&…...

Python机器学习入门笔记(3)—— 线性回归

目录 线性回归 算法简述 LinearRegression() API SGDRegressor API LinearRegression() 和 SGDRegressor对比 过拟合与欠拟合 岭回归 应用场景 线性回归 算法简述 线性回归是一种基本的机器学习算法&#xff0c;它用于建立自变量和因变量之间的线性关系模型。它假设…...

Java:顶级Java应用程序服务器 — Tomcat、Jetty、GlassFish、WildFly

如果你想编写Java web应用程序&#xff0c;首先需要做出一个艰难的决定&#xff1a;选择运行应用程序的Java应用程序服务器。什么是应用服务器?一般来说&#xff0c;应用程序服务器执行Java应用程序。在操作系统中启动它们&#xff0c;然后将应用程序部署到其中。将应用程序服…...

如何在SpringBoot项目上让接口返回数据脱敏,一个注解即可

1 背景需求是某些接口返回的信息&#xff0c;涉及到敏感数据的必须进行脱敏操作2 思路①要做成可配置多策略的脱敏操作&#xff0c;要不然一个个接口进行脱敏操作&#xff0c;重复的工作量太多&#xff0c;很显然违背了“多写一行算我输”的程序员规范。思来想去&#xff0c;定…...

python 之 海龟绘图(turtle)

注&#xff1a;从个人博客园移植而来 使用简介 python 2.6引入的一个简单的绘图工具&#xff0c;俗称为海龟绘图。3.x以上使用的话&#xff0c;可通过pip进行安装&#xff0c;命令为&#xff1a; pip/pip3 install turtle如果出现如下错误&#xff1a; 解决方式&#xff1a; …...

RT-Thread SPI使用教程

RT-Thread SPI 使用教程 实验环境使用的是正点原子的潘多拉开发板。 SPI从机设备使用的是BMP280温湿度大气压传感器。 使用RT-Thread Studio搭建基础功能。 1. 创建工程 使用RT-Thread Studio IDE创建芯片级的工程。创建完成后&#xff0c;可以直接编译下载进行测试。 2.…...

shiro使用——整合spring

shiro使用——整合spring 1. 引入相关配置 <dependency><groupId>org.apache.shiro</groupId><artifactId>shiro-spring</artifactId><version>1.9.1</version></dependency>2. 自定义Realm类 继承AuthorizingRealm 并重写相…...

2023-02-20 leetcode-AccountsMerge

摘要: 记录对leetcode-AccountsMerge的反思 要求: Given a list accounts, each element accounts[i] is a list of strings, where the first element accounts[i][0] is a name, and the rest of the elements are emails representing emails of the account. * Now, w…...

中国高速公路行业市场规模及未来发展趋势

中国高速公路行业市场规模及未来发展趋势编辑中国高速公路行业市场规模正在迅速增长。随着中国经济的快速发展和城市化的加速&#xff0c;对交通基础设施的需求也在不断增加。高速公路是最有效的交通工具&#xff0c;可以大大缩短交通时间&#xff0c;提高出行效率。因此&#…...

STM32大棚花卉物联网护养系统设计与实现

1. 项目概述这个大棚花卉护养系统是我去年为一个花卉种植基地设计的物联网解决方案。当时客户反映传统人工管理方式效率低下&#xff0c;经常出现浇水不及时、温度控制不精准等问题。经过三个月的开发和调试&#xff0c;这套系统成功将花卉产量提升了30%&#xff0c;同时减少了…...

短视频 SEO 优化对于新手有什么建议_如何分析短视频的 SEO 效果

短视频 SEO 优化对于新手有什么建议 在当今数字化时代&#xff0c;短视频平台已经成为了人们获取信息和娱乐的重要途径。无论是抖音、快手&#xff0c;还是TikTok&#xff0c;短视频内容的迅速增长引发了广大创作者对SEO&#xff08;搜索引擎优化&#xff09;的关注。对于新手…...

使用vue3+ts构建企业级文件传输管理系统:状态管理、性能优化与用户体验的深度实践

使用vue3+ts构建企业级文件传输管理系统:状态管理、性能优化与用户体验的深度实践 在现代企业应用中,文件传输是核心功能之一。一个高效的传输管理系统不仅需要处理大量文件,还需提供直观的状态反馈、灵活的操作选项和流畅的用户体验。今天,我将分享一个基于Vue 3和TypeSc…...

判断当前页面是否以「添加到主屏幕」应用形态启动 (快捷方式\APP、套壳包等启动)

这里写自定义目录标题判断当前页面是否以「添加到主屏幕」应用形态启动判断当前页面是否以「添加到主屏幕」应用形态启动 /*** 判断当前页面是否以「添加到主屏幕」应用形态启动* - iOS Safari: navigator.standalone* - 标准 PWA: display-mode 为 standalone/fullscreen/min…...

腾讯云记忆服务,让智能助理进化升级

4月3日消息&#xff0c;腾讯云近日推出“Agent Memory”记忆服务&#xff0c;为智能助理OpenClaw补全长期记忆能力。接入该服务后&#xff0c;OpenClaw回答准确率大幅提升&#xff0c;还支持多种部署方式。创新记忆服务诞生腾讯云数据库团队自主研发了“Agent Memory”记忆服务…...

AI 模型推理延迟与吞吐率的权衡

AI模型推理延迟与吞吐率的权衡&#xff1a;优化策略与实践 在AI应用场景中&#xff0c;模型推理的延迟&#xff08;Latency&#xff09;和吞吐率&#xff08;Throughput&#xff09;是衡量系统性能的两大核心指标。延迟指单次请求的响应时间&#xff0c;直接影响用户体验&…...

Docker 快速通关

一、Docker 大致介绍 Docker 可以帮助我们完成应用的 运行&#xff08;run&#xff09;、构建&#xff08;build&#xff09; 和 分享&#xff08;share&#xff09;。 它的核心目标很简单&#xff1a; 把应用和环境打包起来让应用在不同机器上尽量保持一致方便部署、迁移和…...

洛谷 P2015:二叉苹果树 ← 有依赖的背包问题

【题目来源】 https://www.luogu.com.cn/problem/P2015 【题目描述】 有一棵苹果树&#xff0c;如果树枝有分叉&#xff0c;一定是分二叉&#xff08;就是说没有只有一个儿子的结点&#xff09;。 这棵树共有 N 个结点&#xff08;叶子点或者树枝分叉点&#xff09;&#xff0…...

考研408计算机学科专业基础综合 数据结构复习

考研408计算机学科专业基础综合 数据结构复习 第一页&#xff1a;数据结构&#xff08;一&#xff09;——基础线性表&#xff08;高频&#xff09; 一、数据结构核心基础&#xff08;必背&#xff09; 1. 数据结构定义&#xff1a;相互之间存在一种或多种特定关系的数据元素的…...

暖心指南:儿童心理医院真实案例分享

行业痛点分析当前长沙地区儿童心理健康服务面临多重技术挑战。数据显示&#xff0c;2023年长沙市0-18岁青少年中&#xff0c;约有18.6%存在不同程度的情绪或行为问题&#xff0c;其中焦虑障碍、注意力缺陷多动障碍&#xff08;ADHD&#xff09;及学习困难占比超六成&#xff0c…...