【项目】基于C++11实现的数据库连接池

这篇具有很好参考价值的文章主要介绍了【项目】基于C++11实现的数据库连接池。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

前置知识

关键技术点

MySQL数据库编程、单例模式、queue队列容器、C++11多线程编程、线程互斥、线程同步通信和unique_lock、基于CAS的原子整形、智能指针shared_ptr、lambda表达式、生产者-消费者线程模型

项目背景

MySQL是一个基于C/S设计的关系型数据库管理系统,一条SQL的执行需要通过mysql client发起一个连接,经过TCP三次握手完成TCP连接,然后再对客户端进行身份验证,验证成功后再把SQL发给mysql server(RDBMS)执行SQL(一般会涉及磁盘IO),然后给客户端返回执行结果,执行结束后,进行四次挥手断开连接

如果想要提高MySQL数据库(基于C/S设计)的访问瓶颈:

  • 在服务器端增加缓存服务器,用户缓存常用的数据(例如redis),减少磁盘IO的次数
  • 还可以使用连接池,来提高MySQL Server的访问效率

在高并发情况下:大量的TCP三次握手建立MySQL Server连接认证 以及 TCP四次挥手 MySQL Server关闭连接回收资源所耗费的性能时间也是很明显的,使用连接池就是为了减少这一部分的性能损耗


连接池功能点介绍

该项目是基于C++语言实现的连接池,主要也是实现几个所有连接池都支持的通用基础功能,连接池一般包含了以下内容:

  • 数据库连接所用的ip地址
  • port端口号
  • 用户名和密码,连接哪个库
  • 以及连接池的性能参数,例如 初始连接量,最大连接量,最大空闲时间、连接超时时间等,

1.初始连接量 i n i t S i z e initSize initSize):表示连接池会预先和MySQL Server创建 i n i t S i z e initSize initSize个连接,当用户发起MySQL访问时,不需要创建新的连接,直接从连接池中获取一个可用的连接就可以,使用完成后,并不去释放该连接,而是把当前连接重新归还到连接池当中

2.最大连接量 m a x S i z e maxSize maxSize):当并发访问MySQL Server的请求增多时,初始连接量已经不够使用的时候,此时会根据新的请求数量去创建更多的连接给用户去使用,但是新创建的连接数量上限是 m a x S i z e maxSize maxSize,不能无限制的创建连接。

  • 因为每一个连接都会占用一个 s o c k e t socket socket资源,一般连接池和服务器程序是部署在一台主机上的,如果连接池占用过多的 s o c k e t socket socket资源,那么服务器就不能接收太多的客户端请求了。当这些连接使用完成后,再次归还到连接池当中来维护

3.最大空闲时间 m a x I d l e T i m e maxIdleTime maxIdleTime):当访问MySQL Server的并发请求多了以后,连接池里面的连接数量会动态增加,上限是 m a x S i z e maxSize maxSize个,当这些连接用完再次归还到连接池当中。如果在指定的 m a x I d l e T i m e maxIdleTime maxIdleTime里面,这些新增加的连接都没有被再次使用过,那么新增加的这些连接资源就要被回收掉,只需要保持初始连接量 i n i t S i z e initSize initSize个连接就可以了

4.连接超时时间 c o n n e c t i o n T i m e o u t connectionTimeout connectionTimeout):当MySQL Server的并发请求量过大,连接池中的连接数量已经到达 m a x S i z e maxSize maxSize了,而此时没有空闲的连接可供使用,那么此时用户无法从连接池获取连接,它通过"阻塞"的方式获取连接的时间如果超过 c o n n e c t i o n T i m e o u t connectionTimeout connectionTimeout,那么获取连接失败,无法访问数据库


MySQL Server参数介绍

show variables like 'max_connections';  #查看MySQL Server所支持的最大连接个数

超过 m a x _ c o n n e c t i o n s max\_connections max_connections数量的连接,MySQL Server会直接拒绝访问,所以在使用连接池增加连接数量的时候,MySQL Server的 m a x c o n n e c t i o n s max_connections maxconnections参数也要适当的进行调整,以适配连接池的连接上限

【项目】基于C++11实现的数据库连接池,c++,数据库,adb,开发语言


功能设计

文件 功能
$ConnectionPool.cpp $ 和 C o n n e c t i o n P o o l . h ConnectionPool.h ConnectionPool.h 实现连接池
C o n n e c t i o n . c p p Connection.cpp Connection.cpp C o n n e c t i o n . h Connection.h Connection.h 描述每一条建立的连接:数据库操作代码、增删改查代码实现

连接池功能点介绍

1.连接池只需要一个实例,所以采用单例模式进行设计

2.服务器一般是多线程,可能多个线程都发起了对这个Mysql Server的操作请求,都需要从队列当中获取连接空闲连接,而 C o n n e c t i o n Connection Connection全部维护在一个连接队列中 => 所以需要保证连接队列的线程安全,需要使用互斥锁保证队列的线程安全

3.如果连接队列为空,还需要再获取连接,此时需要动态创建连接,上限数量是 m a x S i z e maxSize maxSize

4.连接队列中空闲连接时间超过 m a x I d l e T i m e maxIdleTime maxIdleTime的就要被释放掉,只保留初始的 i n i t S i z e initSize initSize个连接就可以了,这个功能点肯定需要放在独立的线程中去做

5.如果连接队列为空,而此时连接的数量已达上限 m a x S i z e maxSize maxSize,客户**“阻塞”**等待 c o n n e c t i o n T i m e o u t connectionTimeout connectionTimeout时间之后还没有获取到空闲的连接,那么获取连接失败

  • 此处"阻塞"从Connection队列获取空闲连接,可以使用带超时时间的mutex互斥锁来实现连接超时时间
  • 假设连接超时时间为100ms => 并不是直接睡眠100ms,而是在这100ms时间内,不断判断是否连接队列当中是否有空闲连接,如果有,那么直接获取队头的连接,否则连接池队列为空,就获取失败

6.用户获取的连接需要用shared_ptr智能指针来管理,需要定制删除器 定制 连接释放的功能(此处并不是真正释放连接,而是把连接归还到连接池中)

7.新连接的生产线程 和 获取连接的线程 采用生产者-消费者线程模型来设计,所以需要使用线程间的同步通信机制来保证 => 条件变量和互斥锁


具体流程

假设我们的服务器给客户提供服务,客户端发起请求需要数据库操作时,Server需要到连接池管理的队列中获取一个连接,然后连接池给Server返回一个智能指针维护的连接,Server只管使用这条连接,无需关心这条连接的释放,然后使用这条连接去访问MySQL Server
【项目】基于C++11实现的数据库连接池,c++,数据库,adb,开发语言


开发平台选型

有关MySQL数据库编程、多线程编程、线程互斥和同步通信操作、智能指针、设计模式、容器等等这些技术在C++语言层面都可以直接实现,因此该项目选择直接在windows平台上进行开发

当然,因为采用的都是语言级别的接口,没有强依赖系统的接口,所以跨平台性比较好:放在Linux平台下用g++也可以直接编译运行,但是需要解决一些库的依赖问题


关于MySQL数据库编程

MySQL的windows安装文件云盘地址如下(下载development开发版:包含mysql头文件和libmysql库文件):
链接:https://pan.baidu.com/s/1Y1l7qvpdR2clW5OCdOTwrQ			提取码:95de

MySQL数据库编程直接采用oracle公司提供的MySQL C/C++客户端开发包,在VS上需要进行相应的头文件和库文件的配置,如下

  • 1.右键项目 - C/C++ - 常规 - 附加包含目录,填写下载好的mysql.h头文件在当前电脑的路径
  • 2.右键项目 - 链接器 - 常规 - 附加库目录,填写libmysql.lib的路径
  • 3.右键项目 - 链接器 - 输入 - 附加依赖项,填写libmysql.lib库的名字
  • 4.把 l i b m y s q l . d l l libmysql.dll libmysql.dll动态链接库(Linux下后缀名是.so库)放在工程目录下

坑点:如果MySQL装的是64位版本的,所以动态库什么的都是64位生成的,所以项目先选成64位的

【项目】基于C++11实现的数据库连接池,c++,数据库,adb,开发语言


MySQL接口介绍

初始化:mysql_init()

要使用库,必须先进行初始化 由此也可以看出MySQL其实是网络服务,句柄就是文件描述符

MYSQL *my = mysql_init(nullptr);

链接数据库mysql_real_connect() :

初始化完毕之后,必须先链接数据库,再进行后续操作,因为mysql网络部分是基于TCP/IP的文章来源地址https://www.toymoban.com/news/detail-729061.html

MYSQL *mysql_real_connect

到了这里,关于【项目】基于C++11实现的数据库连接池的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • Java(一):创建 Spring Boot 项目并实现连接操作MySQL数据库

    MySQL 命令 Maven 相关地址 下载地址: https://maven.apache.org/ maven配置方法地址: https://developer.aliyun.com/mvn/guide 仓库搜索地址: https://mvnrepository.com/ https://repo.maven.apache.org/ maven 本地配置 conf/settings.xml 下载 idea 并配置本地环境 maven Maven 构建 生命周期 Maven 的构建 生命周期 包括 三

    2024年02月07日
    浏览(65)
  • 【Android入门到项目实战--4.8】—— 如何查看数据库?(adb)

    目录 什么是adb? 配置adb 使用adb 本文使用adb shell来查看数据库。         adb是Android SDK中自带的一个调试工具,可以直接对连接在电脑上的手机或模拟器进行调试操作,它存放在sdk的platform-tools目录里,如果想在命令行中使用,先把它的路径配置到环境变量里。       

    2024年02月15日
    浏览(35)
  • 基于Qt数据库项目实现(Sqlite3为例)|考查数据库、表格(QTableView 显示)(进阶)

    01 数据库表格(QTableView 显示) 本小节设计一个生活中的例子,使用数据库修改/查询员工的编号、姓名、年龄、性别与照片信息。 本例将数据库的内容显示到 QTableView 上。如果只是简单的显示数据库的内容到QTableView 上,可以使用下面的方法,此方法 QTableView 上可以看到

    2024年02月20日
    浏览(46)
  • 企业级开发项目实战——基于RabbitMQ实现数据库、elasticsearch的数据同步

    1、商品上架时:search-service新增商品到elasticsearch 2、商品下架时:search-service删除elasticsearch中的商品 数据同步是希望,当我们商品修改了数据库中的商品信息,索引库中的信息也会跟着改。在微服务中数据库和索引库是在两个不同的服务中。如果,商品的服务,向es的服务中

    2024年02月12日
    浏览(65)
  • 基于Qt数据库项目实现(Sqlite3为例)|考查数据库、绘制(画家)、事件等知识点(进阶)

    坚持最初的梦想,扬帆起航,乘风破浪,永不言败。 01 数据库 数据库是什么?简易言之,就是保存数据的文件。可以存储大量数据,包括插入数据、更新数据、截取数据等。用专业术语来说,数据库是“按照数据结构来组织、存储和管理数据的仓库”。是一个长期存储在计

    2024年02月19日
    浏览(45)
  • java项目实现读写分离,项目连接Linux部署的数据库异常javax.net.ssl.SSLHandshakeException: No appropriate protocol

    1、对项目进行优化实现读写分离,项目启动时报错如下: Caused by: javax.net.ssl.SSLHandshakeException: No appropriate protocol (protocol is disabled or cipher suites are inappropriate) 原因:javax.net.ssl.SSLHandshakeException:没有适当的协议(协议被禁用或密码套件不合适) 2、bug解决:     注意: useSSL=f

    2024年02月04日
    浏览(51)
  • SpringBoot项目连接数据库

    1、找到applications.yml,如下图  2、写入代码  

    2024年02月15日
    浏览(40)
  • 基于微信小程序的课程点名签到系统设计与实现 报告+项目源码及数据库文件

    题目:微信点名系统小程序 目录 第一节 系统分析与设计 1.1 需求分析 1.2 数据库设计 1.2.1 数据库模型图(初步设计) 1.3 系统功能设计 第二节 系统开发及实现 2.1 系统开发平台及工具 2.2 系统页面及使用说明 2.1.2 学生签到页面(首页) 2.1.3 学生查询页面(课程、我的) 2.

    2024年02月12日
    浏览(45)
  • .NET6项目连接数据库方式方法

    接上一篇Linux系统下创建dotnet项目,这一篇我们聊聊.NET6环境下dotnet项目连接数据库的方式方法,包括数据库字符串该如何配置。看了很多博主写的文章,连接数据库字符串配置的方式和位置五花八门,这篇文章给大家介绍一下连接数据库字符串的配置方式方法,顺便介绍下一

    2024年02月04日
    浏览(52)
  • Java项目:基于ssm框架实现的电影评论系统(ssm+B/S架构+源码+数据库+毕业论文)

    本项目是一套ssm826基于ssm框架实现的电影评论系统,主要针对计算机相关专业的正在做毕设的学生与需要项目实战练习的Java学习者。 包含:项目源码、数据库脚本等,该项目附带全部源码可作为毕设使用。 项目都经过严格调试,eclipse 确保可以运行! 该系统功能完善、界面

    2024年01月25日
    浏览(50)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包