连接池 订阅
连接池是创建和管理一个连接的缓冲池的技术,这些连接准备好被任何需要它们的线程使用。 展开全文
连接池是创建和管理一个连接的缓冲池的技术,这些连接准备好被任何需要它们的线程使用。
信息
性    质
创建和管理连接的缓冲池的技术
外文名
Connection Pool
中文名
连接池
连接池好处
这种连接“汇集”起来的技术基于这样的一个事实:对于大多数应用程序,当它们正在处理通常需要数毫秒完成的事务时,仅需要能够访问JDBC连接的 1 个线程。当不处理事务时,这个连接就会闲置。相反,连接池允许闲置的连接被其它需要的线程使用。事实上,当一个线程需要用 JDBC 对一个 GBase 或其它数据库操作时,它从池中请求一个连接。当这个线程使用完了这个连接,将它返回到连接池中,这样这就可以被其它想使用它的线程使用。当连接从池中“借出”,它被请求它的线程专有地使用。从编程的角度来看,这和用户的线程每当需要一个 JDBC 连接的时候调用DriverManager.getConnection() 是一样的,采用连接池技术,可通过使用新的或已有的连接结束线程。连接池可以极大的改善用户的 Java 应用程序的性能,同时减少全部资源的使用。连接池主要的优点有:减少连接创建时间虽然与其它数据库相比 GBase 提供了较为快速连接功能,但是创建新的 JDBC 连接仍会招致网络和 JDBC 驱动的开销。如果这类连接是“循环”使用的,使用该方式这些花销就可避免。简化的编程模式当使用连接池时,每一个单独的线程能够像创建了一个自己的 JDBC 连接一样操作,允许用户直接使用JDBC编程技术。受控的资源使用如果用户不使用连接池,而是每当线程需要时创建一个新的连接,那么用户的应用程序的资源使用会产生非常大的浪费并且可能会导致高负载下的异常发生。注意,每个连到 GBase 的连接在客户端和服务器端都有花销(内存,CPU,上下文切换等等)。每个连接均会对应用程序和 GBase 服务器的可用资源带来一定的限制。不管这些连接是否在做有用的工作,仍将使用这些资源中的相当一部分。连接池能够使性能最大化,同时还能将资源利用控制在一定的水平之下,如果超过该水平,应用程序将崩溃而不仅仅是变慢。
收起全文
精华内容
下载资源
问答
  • RabbitMQ连接池+SpringBoot实现。通过连接池实现将高效的管理RabbitMQ的Connection,并与springboot进行整合,实现消息发送,获取队列列表等功能。基于此可以进行更多功能的扩充。
  • RabbitMQ客户连接池的Java实现。我们刚开始也是采用这种方式来实现的,但做压力测试时,发现这种每次新建Connection和新建Channel是非常耗时的,在大并发下,一般都要8毫秒左右,慢的话,好多都是几十毫秒。因此我们...
  • java jdbc 连接池实例 项目只要配数据源就可以直接启用, 也可以整合到你个项目里面, 可oracle、mysql、sqlserver自由切换方言。
  • kafka生产者连接池

    2015-05-12 11:51:30
    封装抽取了一个kafka生产者的连接池,能很好的用池的方式对kafka生产者连接点进行有效的管理
  • Spring mvc整合redis实例(redis连接池) 将所有jedis 增删改进行事务的封装、查询单独做为有返回参数的封装。简化了很多代码
  • RabbitMQ客户端连接池的原理及源码

    热门讨论 2015-04-18 19:24:15
    RabbitMQ客户端连接池的原理及源码,经过仔细功能测试和性能测试的
  • 有测试代码和注释。可以参考,代码并不完美,很多地方可以修改,还望高手指点。
  • 最新版阿里数据库连接池Druid-1.1.2.jar
  • 什么是连接池 数据库连接池负责分配、管理和释放数据库连接,它允许应用程序重复使用一个现有的数据库连接,而不是再重新建立一个。 为什么要使用连接池  数据库连接是一种关键的有限的昂贵的资源,这一点在多...

    什么是连接池

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

    为什么要使用连接池

     数据库连接是一种关键的有限的昂贵的资源,这一点在多用户的网页应用程序中体现得尤为突出。  一个数据库连接对象均对应一个物理数据库连接,每次操作都打开一个物理连接,使用完都关闭连接,这样造成系统的 性能低下。 数据库连接池的解决方案是在应用程序启动时建立足够的数据库连接,并讲这些连接组成一个连接池(简单说:在一个“池”里放了好多半成品的数据库联接对象),由应用程序动态地对池中的连接进行申请、使用和释放。对于多于连接池中连接数的并发请求,应该在请求队列中排队等待。并且应用程序可以根据池中连接的使用率,动态增加或减少池中的连接数。 连接池技术尽可能多地重用了消耗内存地资源,大大节省了内存,提高了服务器地服务效率,能够支持更多的客户服务。通过使用连接池,将大大提高程序运行效率,同时,我们可以通过其自身的管理机制来监视数据库连接的数量、使用情况等。 

    传统的连接机制与数据库连接池的运行机制区别

    不使用连接池流程

    下面以访问MySQL为例,执行一个SQL命令,如果不使用连接池,需要经过哪些流程。

    不使用数据库连接池的步骤:

    1. TCP建立连接的三次握手
    2. MySQL认证的三次握手
    3. 真正的SQL执行
    4. MySQL的关闭
    5. TCP的四次握手关闭

    可以看到,为了执行一条SQL,却多了非常多我们不关心的网络交互。

    优点:

    1. 实现简单

    缺点:

    1. 网络IO较多
    2. 数据库的负载较高
    3. 响应时间较长及QPS较低
    4. 应用频繁的创建连接和关闭连接,导致临时对象较多,GC频繁
    5. 在关闭连接后,会出现大量TIME_WAIT 的TCP状态(在2个MSL之后关闭)

    使用连接池流程

    使用数据库连接池的步骤:

    第一次访问的时候,需要建立连接。 但是之后的访问,均会复用之前创建的连接,直接执行SQL语句。

    优点:

    1. 较少了网络开销
    2. 系统的性能会有一个实质的提升
    3. 没了麻烦的TIME_WAIT状态

    数据库连接池的工作原理

    连接池的工作原理主要由三部分组成,分别为

    1. 连接池的建立
    2. 连接池中连接的使用管理
    3. 连接池的关闭

            第一、连接池的建立。一般在系统初始化时,连接池会根据系统配置建立,并在池中创建了几个连接对象,以便使用时能从连接池中获取。连接池中的连接不能随意创建和关闭,这样避免了连接随意建立和关闭造成的系统开销。Java中提供了很多容器类可以方便的构建连接池,例如Vector、Stack等。

            第二、连接池的管理。连接池管理策略是连接池机制的核心,连接池内连接的分配和释放对系统的性能有很大的影响。其管理策略是:

            当客户请求数据库连接时,首先查看连接池中是否有空闲连接,如果存在空闲连接,则将连接分配给客户使用;如果没有空闲连接,则查看当前所开的连接数是否已经达到最大连接数,如果没达到就重新创建一个连接给请求的客户;如果达到就按设定的最大等待时间进行等待,如果超出最大等待时间,则抛出异常给客户。

            当客户释放数据库连接时,先判断该连接的引用次数是否超过了规定值,如果超过就从连接池中删除该连接,否则保留为其他客户服务。

            该策略保证了数据库连接的有效复用,避免频繁的建立、释放连接所带来的系统资源开销。

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

    连接池主要参数

    使用连接池时,要配置一下参数

    1. 最小连接数:是连接池一直保持的数据库连接,所以如果应用程序对数据库连接的使用量不大,将会有大量的数据库连接资源被浪费.
    2. 最大连接数:是连接池能申请的最大连接数,如果数据库连接请求超过次数,后面的数据库连接请求将被加入到等待队列中,这会影响以后的数据库操作
    3. 最大空闲时间
    4. 获取连接超时时间
    5. 超时重试连接次数

    连接池需要注意的点

    1、并发问题

      为了使连接管理服务具有最大的通用性,必须考虑多线程环境,即并发问题。这个问题相对比较好解决,因为各个语言自身提供了对并发管理的支持像java,c#等等,使用synchronized(java)lock(C#)关键字即可确保线程是同步的。使用方法可以参考,相关文献。

    2、事务处理

      我们知道,事务具有原子性,此时要求对数据库的操作符合“ALL-OR-NOTHING”原则,即对于一组SQL语句要么全做,要么全不做。 
      我们知道当2个线程共用一个连接Connection对象,而且各自都有自己的事务要处理时候,对于连接池是一个很头疼的问题,因为即使Connection类提供了相应的事务支持,可是我们仍然不能确定那个数据库操作是对应那个事务的,这是由于我们有2个线程都在进行事务操作而引起的。为此我们可以使用每一个事务独占一个连接来实现,虽然这种方法有点浪费连接池资源但是可以大大降低事务管理的复杂性。 

    3、连接池的分配与释放

      连接池的分配与释放,对系统的性能有很大的影响。合理的分配与释放,可以提高连接的复用度,从而降低建立新连接的开销,同时还可以加快用户的访问速度。 
      对于连接的管理可使用一个List。即把已经创建的连接都放入List中去统一管理。每当用户请求一个连接时,系统检查这个List中有没有可以分配的连接。如果有就把那个最合适的连接分配给他(如何能找到最合适的连接文章将在关键议题中指出);如果没有就抛出一个异常给用户,List中连接是否可以被分配由一个线程来专门管理捎后我会介绍这个线程的具体实现。

    4、连接池的配置与维护

      连接池中到底应该放置多少连接,才能使系统的性能最佳?系统可采取设置最小连接数(minConnection)和最大连接数(maxConnection)等参数来控制连接池中的连接。比方说,最小连接数是系统启动时连接池所创建的连接数。如果创建过多,则系统启动就慢,但创建后系统的响应速度会很快;如果创建过少,则系统启动的很快,响应起来却慢。这样,可以在开发时,设置较小的最小连接数,开发起来会快,而在系统实际使用时设置较大的,因为这样对访问客户来说速度会快些。最大连接数是连接池中允许连接的最大数目,具体设置多少,要看系统的访问量,可通过软件需求上得到。 
      如何确保连接池中的最小连接数呢?有动态和静态两种策略。动态即每隔一定时间就对连接池进行检测,如果发现连接数量小于最小连接数,则补充相应数量的新连接,以保证连接池的正常运转。静态是发现空闲连接不够时再去检查。

    数据库对比

    第一、二代连接池

    区分一个数据库连接池是属于第一代产品还是代二代产品有一个最重要的特征就是看它在架构和设计时采用的线程模型,因为这直接影响的是并发环境下存取数据库连接的性能。

    一般来讲采用单线程同步的架构设计都属于第一代连接池,二采用多线程异步架构的则属于第二代。比较有代表性的就是Apache Commons DBCP,在1.x版本中,一直延续着单线程设计模式,到2.x才采用多线程模型。

    用版本发布时间来辨别区分两代产品,则一个偷懒的好方法。以下是这些常见数据库连接池最新版本的发布时间:

    数据库连接池

    最新版本

    发布时间

    C3P0

    c3p0-0.9.5.2

    on 9 Dec 2015

    DBCP

    2.2.0

    27 December 2017

    Druid

    0.11.0

    Dec 4 2017

    HikariCP

    2.7.6

    2018-01-14

    从表中可以看出,C3P0已经很久没有更新了。DBCP更新速度很慢,基本处于不活跃状态,而Druid和HikariCP处于活跃状态的更新中,这就是我们说的二代产品了。

    二代产品对一代产品的超越是颠覆性的,除了一些“历史原因”,你很难再找到第二条理由说服自己不选择二代产品,但任何成功都不是偶然的,二代产品的成功很大程度上得益于前代产品们打下的基础,站在巨人的肩膀上,新一代的连接池的设计师们将这一项“工具化”的产品,推向了极致。其中,最具代表性的两款产品是:

    • HikariCP
    • Druid

    彻底死掉的C3P0

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

    咸鱼翻身的DBCP

    DBCP(DataBase Connection Pool)属于Apache顶级项目Commons中的核心子项目(最早在Jakarta Commons里就有),在Apache的生态圈中的影响里十分广泛,比如最为大家所熟知的Tomcat就在内部集成了DBCP,实现JPA规范的OpenJPA,也是默认集成DBCP的。但DBCP并不是独立实现连接池功能的,它内部依赖于Commons中的另一个子项目Pool,连接池最核心的“池”,就是由Pool组件提供的,因此,DBCP的性能实际上就是Pool的性能,DBCP和Pool的依赖关系如下表:

    Apache Commons DBCP

    Apache Commons Pool

    v1.2.2

    v1.3

    v1.3

    v1.5.4

    v1.4

    v1.5.4

    v2.0.x

    v2.2

    v2.1.x

    v2.4.2

    v2.2.x

    v2.5.0

    可以看到,因为核心功能依赖于Pool,所以DBCP本身只能做小版本的更新,真正大版本的更迭则完全依托于pool。有很长一段时间,pool都还是停留在1.x版本,这直接导致DBCP也更新乏力。很多依赖DBCP的应用在遇到性能瓶颈之后,别无选择,只能将其替换掉,DBCP忠实的拥趸tomcat就在其tomcat 7.0版本中,自己重新设计开发出了一套连接池(Tomcat JDBC Pool)。好在,在2013年事情终于迎来转机,13年9月Commons-Pool 2.0版本发布,14年2月份,DBCP也终于迎来了自己的2.0版本,基于新的线程模型全新设计的“池”让DBCP重焕青春,虽然和新一代的连接池相比仍有一定差距,但差距并不大,DBCP2.x版本已经稳稳达到了和新一代产品同级别的性能指标(见下图)。

    DBCP终于靠Pool咸鱼翻身,打了一个漂亮的翻身仗,但长时间的等待已经完全消磨了用户的耐心,与新一代的产品项目相比,DBCP没有任何优势,试问,谁会在有选择的前提下,去选择那个并不优秀的呢?也许,现在还选择DBCP2的唯一理由,就是情怀吧。

    性能无敌的HikariCP

    HikariCP号称“性能杀手”(It’s Faster),它的表现究竟如何呢,先来看下官网提供的数据:

    不光性能强劲,稳定性也不差:

    那它是怎么做到如此强劲的呢?官网给出的说明如下:

    • 字节码精简:优化代码,直到编译后的字节码最少,这样,CPU缓存可以加载更多的程序代码;
    • 优化代理和拦截器:减少代码,例如HikariCP的Statement proxy只有100行代码;
    • 自定义数组类型(FastStatementList)代替ArrayList:避免每次get()调用都要进行range check,避免调用remove()时的从头到尾的扫描;
    • 自定义集合类型(ConcurrentBag):提高并发读写的效率;
    • 其他缺陷的优化,比如对于耗时超过一个CPU时间片的方法调用的研究(但没说具体怎么优化)。

    可以看到,上述这几点优化,和现在能找到的资料来看,HakariCP在性能上的优势应该是得到共识的,再加上它自身小巧的身形,在当前的“云时代、微服务”的背景下,HakariCP一定会得到更多人的青睐。

    功能全面的Druid

    近几年,阿里在开源项目上动作频频,除了有像fastJson、dubbo这类项目,更有像AliSQL这类的大型软件,今天说的Druid,就是阿里众多优秀开源项目中的一个。它除了提供性能卓越的连接池功能外,还集成了SQL监控,黑名单拦截等功能,用它自己的话说,Druid是“为监控而生”。借助于阿里这个平台的号召力,产品一经发布就赢得了大批用户的拥趸,从用户使用的反馈来看,Druid也确实没让用户失望。

    相较于其他产品,Druid另一个比较大的优势,就是中文文档比较全面(毕竟是国人的项目么),在github的wiki页面,列举了日常使用中可能遇到的问题,对一个新用户来讲,上面提供的内容已经足够指导它完成产品的配置和使用了。

    下图为Druid自己提供的性能测试数据:

    现在项目开发中,我还是比较倾向于使用Durid,它不仅仅是一个数据库连接池,它还包含一个ProxyDriver,一系列内置的JDBC组件库,一个SQL Parser。

    Druid 相对于其他数据库连接池的优点

    1. 强大的监控特性,通过Druid提供的监控功能,可以清楚知道连接池和SQL的工作情况。

    a. 监控SQL的执行时间、ResultSet持有时间、返回行数、更新行数、错误次数、错误堆栈信息;

    b. SQL执行的耗时区间分布。什么是耗时区间分布呢?比如说,某个SQL执行了1000次,其中0~1毫秒区间50次,1~10毫秒800次,10~100毫秒100次,100~1000毫秒30次,1~10秒15次,10秒以上5次。通过耗时区间分布,能够非常清楚知道SQL的执行耗时情况;

    c. 监控连接池的物理连接创建和销毁次数、逻辑连接的申请和关闭次数、非空等待次数、PSCache命中率等。

    1. 方便扩展。Druid提供了Filter-Chain模式的扩展API,可以自己编写Filter拦截JDBC中的任何方法,可以在上面做任何事情,比如说性能监控、SQL审计、用户名密码加密、日志等等。
    2. Druid集合了开源和商业数据库连接池的优秀特性,并结合阿里巴巴大规模苛刻生产环境的使用经验进行优化。

    总结

    时至今日,虽然每个应用(需要RDBMS的)都离不开连接池,但在实际使用的时候,连接池已经可以做到“隐形”了。也就是说在通常情况下,连接池完成项目初始化配置之后,就再不需要再做任何改动了。不论你是选择Druid或是HikariCP,甚至是DBCP,它们都足够稳定且高效!之前讨论了很多关于连接池的性能的问题,但这些性能上的差异,是相较于其他连接池而言的,对整个系统应用来说,第二代连接池在使用过程中体会到的差别是微乎其微的,基本上不存在因为连接池的自身的配饰和使用导致系统性能下降的情况,除非是在单点应用的数据库负载足够高的时候(压力测试的时候),但即便是如此,通用的优化的方式也是单点改集群,而不是在单点的连接池上死扣。

     

    参考:

    http://rainbowhorse.site/2018/02/06/%E5%A4%A7%E8%AF%9D%E6%95%B0%E6%8D%AE%E5%BA%93%E8%BF%9E%E6%8E%A5%E6%B1%A0/

    https://blog.csdn.net/frightingforambition/article/details/25464129

    https://juejin.im/entry/58fb03220ce4630061233c98

    展开全文
  • 三、数据库连接池的工作原理 连接池的工作原理主要由三部分组成,分别为 连接池的建立 连接池中连接的使用管理 连接池的关闭 第一、连接池的建立。 一般在系统初始化时,连接池会根据系统配置建立,并在池中创建了...

    一、什么是连接池?

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

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

    ———以上参考《百度百科》

    二、为什么使用数据连接池

    建立一个数据库连接是一件非常耗时(消耗时间)耗力(消耗资源)的事情。之所以会这样,是因为连接到数据库服务器需要经历几个漫长的过程:建立物理通道(例如套接字或命名管道),与服务器进行初次握手,分析连接字符串信息,由服务器对连接进行身份验证,运行检查以便在当前事务中登记等等。

    连接池就是这样一个容器:它存放了一定数量的与数据库服务器的物理连接。因此,当我们需要连接数据库服务器的时候,只需去池(容器)中取出一条空闲的连接,而不是新建一条连接。这样的话,我们就可以大大减少连接数据库的开销,从而提高了应用程序的性能。

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

    连接池的工作原理主要由三部分组成,分别为

    • 连接池的建立
    • 连接池中连接的使用管理
    • 连接池的关闭

    第一、连接池的建立。
      一般在系统初始化时,连接池会根据系统配置建立,并在池中创建了几个连接对象,以便使用时能从连接池中获取。连接池中的连接不能随意创建和关闭,这样避免了连接随意建立和关闭造成的系统开销。

    Java中提供了很多容器类可以方便的构建连接池,例如Vector、Stack等。

    第二、连接池的管理。
      连接池管理策略是连接池机制的核心,连接池内连接的分配和释放对系统的性能有很大的影响。其管理策略是:

    当客户请求数据库连接时,

    • 1)如果池中有空闲连接可用,返回该连接。
    • 2)如果没有空闲连接,池中连接都已用完,创建一个新连接添加到池中。
    • 3)如果池中连接已达到最大连接数,请求按设定的最大等待时间进入等待队列直到有空闲连接可用。
    • 4)如果超出最大等待时间,则抛出异常给客户。

    当客户释放数据库连接时,先判断该连接的引用次数是否超过了规定值,如果超过就从连接池中删除该连接,否则保留为其他客户服务。

    该策略保证了数据库连接的有效复用,避免频繁的建立、释放连接所带来的系统资源开销。

    如果连接长时间空闲,或检测到与服务器的连接已断开,连接池管理器也会将该连接从池中移除。

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

    四、连接池需要注意的点

    1、并发问题

    为了使连接管理服务具有最大的通用性,必须考虑多线程环境,即并发问题。

    这个问题相对比较好解决,因为各个语言自身提供了对并发管理的支持像java,c#等等,使用synchronized(java)lock(C#)关键字即可确保线程是同步的。

    2、事务处理

    我们知道,事务具有原子性,此时要求对数据库的操作符合“ALL-OR-NOTHING”原则,即对于一组SQL语句要么全做,要么全不做。

    我们知道当2个线程共用一个连接Connection对象,而且各自都有自己的事务要处理时候,对于连接池是一个很头疼的问题,因为即使Connection类提供了相应的事务支持,可是我们仍然不能确定那个数据库操作是对应那个事务的,这是由于我们有2个线程都在进行事务操作而引起的。

    为此我们可以使用每一个事务独占一个连接来实现,虽然这种方法有点浪费连接池资源但是可以大大降低事务管理的复杂性。

    3、连接池的分配与释放

    连接池的分配与释放,对系统的性能有很大的影响。合理的分配与释放,可以提高连接的复用度,从而降低建立新连接的开销,同时还可以加快用户的访问速度。

    对于连接的管理可使用一个List。即把已经创建的连接都放入List中去统一管理。每当用户请求一个连接时,系统检查这个List中有没有可以分配的连接。如果有就把那个最合适的连接分配给他,如果没有就抛出一个异常给用户。

    4、连接池的配置与维护

    连接池中到底应该放置多少连接,才能使系统的性能最佳?

    系统可采取设置**最小连接数(minConnection)最大连接数(maxConnection)**等参数来控制连接池中的连接。

    比方说,最小连接数是系统启动时连接池所创建的连接数。如果创建过多,则系统启动就慢,但创建后系统的响应速度会很快;如果创建过少,则系统启动的很快,响应起来却慢。这样,可以在开发时,设置较小的最小连接数,开发起来会快,而在系统实际使用时设置较大的,因为这样对访问客户来说速度会快些。

    最大连接数是连接池中允许连接的最大数目,具体设置多少,要看系统的访问量,可通过软件需求上得到。

    如何确保连接池中的最小连接数呢?

    有动态和静态两种策略。
    动态即每隔一定时间就对连接池进行检测,如果发现连接数量小于最小连接数,则补充相应数量的新连接,以保证连接池的正常运转。静态是发现空闲连接不够时再去检查。

    展开全文
  • 使用Druid数据连接池连接PostgreSQL简单例子,搭建一个简单测试环境
  • DRUID连接池

    万次阅读 2018-05-23 23:33:02
    DRUID连接池Druid是阿里巴巴开发的号称为监控而生的数据库连接池,Druid是目前最好的数据库连接池。 在功能、性能、扩展性方面,都超过其他数据库连接池,同时加入了日志监控, 可以很好的监控DB池连接和SQL的执行...

    DRUID连接池

    Druid是阿里巴巴开发的号称为监控而生的数据库连接池,Druid是目前最好的数据库连接池。
    在功能、性能、扩展性方面,都超过其他数据库连接池,同时加入了日志监控,
    可以很好的监控DB池连接和SQL的执行情况。
    
    DRUID连接池使用的jar包: druid-1.0.9.jar

    DRUID常用的配置参数

    jdbcUrl 连接数据库的url:mysql : jdbc:mysql://localhost:3306/testusername 数据库的用户名password 数据库的密码driverClassName 驱动类名。根据url自动识别,这一项可配可不配,如果不配置druid会根据url自动识别dbType,
    然后选择相应的driverClassName(建议配置下)
        
    initialSize初始化时建立物理连接的个数。初始化发生在显示调用init方法,或者第一次 getConnection时maxActive 最大连接池数量maxIdle 已经不再使用,配置了也没效果minIdle 最小连接池数量maxWait 获取连接时最大等待时间,单位毫秒。

    创建连接池

    //com.alibaba.druid.pool.DruidDataSourceFactory 类有创建连接池的方法
    public static DataSource createDataSource(Properties properties)
    创建一个连接池,连接池的参数使用properties中的数据我们可以看到DRUID连接池在创建的时候需要一个Properties对象来设置参数,
    ​
    所以我们使用properties文件来保存对应的参数。//DRUID连接池的配置文件名称随便,建议放到src目录下面方便加载。 

    druid.properties 文件内容:

    # 配置数据库的连接参数
    driverClassName=com.mysql.jdbc.Driver
    url=jdbc:mysql://127.0.0.1:3306/test
    username=root
    password=root# 配置连接池的参数
    initialSize=5
    maxActive=10
    maxWait=3000
    maxIdle=6
    minIdle=3

    使用步骤

    1. 在src目录下创建一个properties文件,文件名随意,并设置对应参数
    2. 加载properties文件的内容到Properties对象中
    3. 创建DRUID连接池,使用配置文件中的参数
    4. 从DRUID连接池中取出连接
    5. 执行SQL语句
    6. 关闭资源

    案例代码

    在src目录下新建一个DRUID配置文件,命名为:druid.properties,内容如下

    driverClassName=com.mysql.jdbc.Driver
    url=jdbc:mysql://127.0.0.1:3306/test
    username=root
    password=root
    initialSize=5
    maxActive=10
    maxWait=3000
    maxIdle=6
    minIdle=3

    使用DRUID连接池中的连接操作数据库

    public class Demo {
        public static void main(String[] args) throws Exception {
            
        // 加载类路径下,即src目录下的druid.properties这个文件
        InputStream is = Demo.class.getResourceAsStream("/druid.properties");
            
        Properties pp = new Properties();
        pp.load(is);
            
        // 创建连接池,使用配置文件中的参数
        DataSource ds = DruidDataSourceFactory.createDataSource(pp);
            
        // for (int i = 0; i < 10; i++) {
        // Connection conn = ds.getConnection();
        // System.out.println(conn);
        // }
            
        // 从连接池中取出连接
        Connection conn = ds.getConnection();
            
        // 执行SQL语句
        String sql = "INSERT INTO student VALUES (NULL, ?, ?, ?);";
        PreparedStatement pstmt = conn.prepareStatement(sql);
        pstmt.setString(1, "王五");
        pstmt.setInt(2, 35);
        pstmt.setDouble(3, 88.5);
        int i = pstmt.executeUpdate();
        System.out.println("影响的行数: " + i);
            
        // 执行查询
        sql = "SELECT * FROM student;";
        ResultSet rs = pstmt.executeQuery(sql);
        while (rs.next()) {
            int id = rs.getInt("id");
            String name = rs.getString("name");
            int age = rs.getInt("age");
            double score = rs.getDouble("score");
            System.out.println("id: " + id + " ,name: " + name + " ,age = " + age + " ,score =
            " + score);
            }
        pstmt.close();
        conn.close(); // 将连接还回连接池中
        }
    }
    DRUID连接池根据Properties对象中的数据作为连接池参数去创建连接池,
    我们自己定义properties类型的配置文件,名称自己取,也可以放到其他路径,建议放到src目录下方便加载。 
    不管是C3P0连接池,还是DRUID连接池,//配置大致都可以分为2种: 1.连接数据库的参数 , 2.连接池的参数 ,这2种配置大致参数作用都相同,只是参数名称可能不一样。

    连接池工具类

    1)创建私有静态数据源成员变量DataSource ds2)在静态代码块中创建连接池
    a)创建属性对象
    b)从类路径下加载属性文件,得到输入流对象
    c)通过工厂类创建一个数据源3)创建公有的得到数据源的方法getDataSource()
    4)创建得到连接对象的方法 getConnection()
    5)创建释放资源的方法 close()

     /**
     * 连接池的工具类
     */
    public class DataSourceUtils {
    ​
        //创建一个成员变量
        private static DataSource ds;
    ​
        /**
         * 加载的代码写在静态代码块中
         */
        static {
            try {
                Properties info = new Properties();
                //加载类路径下,即src目录下的druid.properties这个文件
                info.load(DataSourceUtils.class.getResourceAsStream("/druid.properties"));
                
                //读取属性文件创建连接池
                ds = DruidDataSourceFactory.createDataSource(info);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    ​
        /**
         * 得到数据源
         */
        public static DataSource getDataSource() {
            return ds;
        }
    ​
    ​
        /**
         * 得到连接对象
         */
        public static Connection getConnection() {
            try {
                return ds.getConnection();
            } catch (SQLException e) {
                throw new RuntimeException(e);
            }
        }
    ​
        /**
         * 释放资源
         */
        public static void close(Connection conn, Statement stmt, ResultSet rs) {
            if (rs!=null) {
                try {
                    rs.close();
                } catch (SQLException e) {
                    e.printStackTrace();
                }
            }
            if (stmt!=null) {
                try {
                    stmt.close();
                } catch (SQLException e) {
                    e.printStackTrace();
                }
            }
            if (conn!=null) {
                try {
                    conn.close();
                } catch (SQLException e) {
                    e.printStackTrace();
                }
            }
        }
    ​
        public static void close(Connection conn, Statement stmt) {
            close(conn, stmt, null);
        }
    }

    数据源工具类的使用

    需求:向学生表中插入1条学生记录

    创建学生表

    create table student (
      id int(11) primary key not null auto_increment,
    ​
      name varchar(20) not null,
    ​
      gender tinyint(1) default null,
    ​
      birthday date default null,
    )
    public class DemoAdd {
        public static void main(String[] args) {
    ​
            //1. 创建连接对象,通过连接池工具类
            Connection conn = null;
            PreparedStatement ps = null;
            int row = 0;
            try {
                conn = DataSourceUtils.getConnection();
                
                //2. 创建语句对象
               ps = conn.prepareStatement("INSERT INTO student values(null,?,?,?)");
               ps.setString(1,"张辽");
               ps.setInt(2,1);
               ps.setString(3,"194-06-16");
                
               //3. 使用executeUpdate()写入到数据库
                row = ps.executeUpdate();
                
            } catch (SQLException e) {
                e.printStackTrace();
            } finally {
    ​
                //4. 释放资源
                DataSourceUtils.close(conn, ps);
            }
    ​
            System.out.println("添加了" + row);
        }
    }

    展开全文
  • 一个封装了MySQL C API的包了连接池的C++封装 CDBConnectionPool 连接池类 CDBConnection 连接对象 CDBRecordset 返回的记录集对象,开发人员只需要操作这个对象 DBDef.h,包含了所有对象定义
  • 数据库连接池

    千次阅读 多人点赞 2019-10-22 19:54:01
    1、什么是数据库连接池? 数据库连接池负责分配、管理和释放数据库连接,它允许应用程序重复使用一个现有的数据库连接,而不是再重新建立一个; 释放空闲时间超过最大空闲时间的数据库连接来避免因为没有释放...

    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 的区别。

     

     

     

     

     

     

     

    展开全文
  • JDBC与数据库连接池

    万次阅读 多人点赞 2018-10-24 23:58:23
    JDBC简介,driver类型,JDBC连接,使用技巧; 连接,短连接,长连接,连接池; 池化思想; 配置,基本配置,关键配置,性能配置; 连接池工具; druid; HikariCP; flexy-pool;
  • 一、连接池的基本概念 1.什么是连接池? 数据库连接池负责分配、管理和释放数据库连接,其基本思想就是为数据库建立一个“缓冲池”,预先在缓冲池中放入一定数量的连接,当需要建立数据库连接时,只需从“缓冲池...
  • 阿里巴巴数据库连接池完整demo

    热门讨论 2014-08-13 13:11:13
    阿里巴巴数据库连接池应该是目前最好的数据库连接池:大并发稳定,操作数据库效率高。此demo不仅有和spring整合的例子,还有单独配置的实例,供大家学习掌握
  • Dbcp连接池-Java项目-3个jar包

    热门讨论 2016-10-08 09:42:03
    dbcp连接池的三个jar包,commons-logging-1.2.jar,commons-dbcp2-2.1.1.jar,commons-pool2-2.4.2.jar,以及jar包的Apache官网下载地址,压缩包内有3个zip包,需要解压得到3个jar包。
  • HikariCP连接池各属性详解

    千次阅读 2020-06-22 17:47:50
    HikariCP是由日本程序员开源的一个数据库连接池组件,代码非常轻量,并且速度非常的快。根据官方提供的数据,在i7,开启32个线程32个连接的情况下,进行随机数据库读写操作,HikariCP的速度是现在常用的C3P0数据库...
  • 如何自己手写一套数据库连接池?

    千次阅读 2020-07-09 23:58:16
    文章目录1、术语介绍2、实现原理3、代码实现3.1连接池配置文件3.2连接池管理3.3连接池接口3.4连接池实现3.5演示代码3.6演示效果说明 关于数据库连接池原理,什么杂七杂八的,本文不再重复啰嗦。有什么不理解的参考...
  • 很棒的数据库多连接池程序,对每个连接可以配置一个连接池,可以对问题连接定时处理,已经在生产上使用,同时支持连接多个数据库,增加修改都支持配置,,所以配置都放置在缓存中,定期刷新。 是用JAVA写的,已经...
  • 文章目录Golang 侧数据库连接池原理和参数调优数据库连接池数据库连接池的设计Go 的数据库连接池Go 数据库连接池的设计建立连接释放连接清理连接配置 sql.DB 以获得更好的性能maxOpenmaxIdlemaxLifeTime在实践和压测...
  • MySQL连接池

    千次阅读 2019-08-15 21:02:16
    选用Mysql连接池的场景 对于简单的数据库查询,由于对于数据库的访问不是很频繁,这时可以在访问数据库时,就新创建一个连接,用完后就关闭它,这样做也不会带来什么明显的性能上的开销。但是对于一个经常访问的...
  • Jedis - Jedis连接池(优化)

    千次阅读 多人点赞 2020-09-22 20:22:28
    Jedis连接池原理(空间换时间,就相当于一个集合)连接池的优势:2.1 Jedis连接池实现(硬编码)2.2 Jedis连接池优化(写成工具类调用) 1. Jedis概述(java客户端操作Redis的工具类)    Jedis是Redis官方推荐使用的Java...
  • spring配置连接池

    千次阅读 2018-09-29 09:34:26
    1、连接池概述  数据库连接是一种关键的有限的昂贵的资源,这一点在多用户的网页应用程序中体现得尤为突出。对数据库连接的管理能显著影响到整个应用程序的伸缩性和健壮性,影响到程序的性能指标。数据库连接池正是...
  • 动态加载数据库连接池

    千次阅读 2019-08-22 09:29:58
    实现背景:对于SQL语句需要在库中配置的数据源加载问题,无法直接使用外部的数据库连接池加载动态配置的数据库 简单的实现方式是使用JDBC单独获取配置信息建立数据库连接,对于连接频繁的数据库连接使用JDBC则不是...
  • 几种常用数据库连接池的使用

    万次阅读 多人点赞 2019-02-14 12:38:38
    一、应用程序直接获取数据库连接的缺点  用户每次请求都需要向数据库获得链接,而数据库创建连接通常需要...二、使用数据库连接池优化程序性能 2.1、数据库连接池的基本概念  数据库连接是一种关键的有限的昂...
  • MyBatis 通过第三方Druid数据连接池连接SQL server 简单例子,使用代理数据源模式
  • 数据库连接池之Druid连接池(mysql)

    千次阅读 多人点赞 2019-04-18 08:27:13
    数据库连接池之Druid连接池(mysql) 本仙鱼又更博了,我是勤劳的小蜜蜂嗡嗡嗡~~ 1 Druid简介 Druid 是目前比较流行的高性能的(阿里的),分布式列存储的OLAP框架(具体来说是MOLAP)。它有如下几个特点: 一. 亚秒级...
  • C#高效数据库连接池源码

    热门讨论 2012-11-20 10:32:30
    C#高效数据库连接池源码

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 529,468
精华内容 211,787
关键字:

连接池