使用JDBC是怎么保证数据库客户端和数据库服务端进行连接的?


通过代码:

  1. conn=DriverManager.getConnection(url, username, password);

JDBC通过这条代码方法的调用建立了一条客户端应用程序到后端数据库的物理连接。期间发生了大量的基于TCP的客户端与服务端的交互。

由于跨机器的网络传输是由较大的网络开销的,所以时间花销很大。

传统的多线程JDBC服务中,我们每进行一次服务都需要分配一个线程,每一个线程去建立一个数据库连接,当这条服务结束之后,该线程和该数据库连接都将被销毁。

当我们需要下一次数据库服务时,再次建立新的线程和数据库连接。

这样每次在建立数据库连接上浪费了大量的时间,用户的相应时间变得很慢。

连接池的出现就是为了解决这个问题,连接池实现了数据库连接(connection对象)的复用,当一个线程处理完相应程序服务,随后不紧接着销毁数据库连接,而是把它交给下一个线程使用。这样就避免了多次建立数据库连接而浪费时间的问题出现。实现了从每个线程创建数据库连接到每个线程租用数据库连接的转变。

MySQL数据库内部是怎么分配各种连接的?


在MySQL数据库中也存在着内存限制,当分配的数据库连接过多,会增加数据库内存的占用,加剧各种锁的冲突,占用数据库资源,甚至造成数据库崩溃。所以一般在MySQL数据库中设置最大连接数。

但是,为了保证不出现上述问题,我们可以在连接请求到达数据库之前进行限流,保证数据库资源的优化利用,效率至上。连接池就起到了这个作用:限制连接。

连接池到底是什么?


连接池本质上就是一组java的jar包,介于java应用和JDBC数据库物理连接之间,帮助应用程序来管理数据库连接,通过连接池暴露的接口,应用程序可以获取JDBC连接,使用完后

将JDBC归还给连接池,供下一个线程使用。

在连接池中,数据库连接不足的时候,会自动创建连接;同时当空闲连接过多时也会自动销毁连接。

当多个线程同时访问时,连接池还提供了排队等待的功能。保证了应用程序有序地获取数据库连接。

连接池怎么使用?(相关示例代码贴在后面)


以现在最受欢迎的JDCP连接池为例。

相关jar包下载地址:

http://commons.apache.org/proper/commons-dbcp/download_dbcp.cgi

http://commons.apache.org/proper/commons-pool/download_pool.cgi

http://commons.apache.org/proper/commons-logging/download_logging.cgi

其中,有两种jar版本,windows推荐下载.zip版

关于两版的差别,参考:

http://blog.csdn.net/suyu_yuan/article/details/52733117

https://www.zhihu.com/question/26026741

1)创建一个连接池对象(BasicDataSource):

因为JDCP的底层也是通过JDBC来实现的,所以我们需要告诉它相应的信息。

通过BasicDataSource对象的一系列方法,来对连接池进行相关设置(基础的和高级的)

相关高级配置:

连接数配置:

其中建议:将setMaxIdle()和setMinIdle()设置为相同的值。

DBCP定期检查:

数据库服务端为了释放空闲等待的资源,默认会自动关闭空闲时间等待超过某个阈值的连接。MySQL默认阈值为8个小时。

但是,连接池不知道那个连接失效了,以防止连接池将失效的连接租借给应用程序,所以需要定期检查。

保证连接池和数据库服务端连接对象同步性,保证,连接池租借给应用程序的连接对象都是有效的。

建议:连接池中连接对象的销毁时间阈值要小于数据库服务器的销毁时间阈值。也就是说要在数据库服务器销毁连接对象前,连接池先销毁连接对象。保证连接池中连接对象的有效性。

2)通过BasicDataSource对象获取数据库连接对象(connection),然后跟JDBC中相似进行相关数据库服务的调用。

注意,我们同样需要在一系列操作过后,调用connection对象的close()方法。

但是连接池重写了connection对象的close()方法,使得它的功能不再是将connection对象销毁,而是将connection对象归还给连接池,以供下一个线程调用。

相关示例代码:


  1. package com.java_JDCP;
  2.  
  3. import java.sql.Connection;
  4. import java.sql.PreparedStatement;
  5. import java.sql.ResultSet;
  6. import java.sql.SQLException;
  7. import java.sql.Statement;
  8.  
  9. import org.apache.commons.dbcp2.BasicDataSource;
  10.  
  11. public class JDCP_test {
  12.  
  13. private static String driverClassName="com.mysql.jdbc.Driver"; //数据库驱动
  14. //连接数据库的URL地址
  15. private static String url="jdbc:mysql://localhost:3306/hellojdbc?useUnicode=true&characterEncoding=UTF-8";
  16. private static String username="root";//数据库连接用户名
  17. private static String password="123456";//数据库连接密码
  18.  
  19. private static Connection conn=null;//数据库连接对象
  20. private static Statement stat=null;//语句陈述对象
  21. private static ResultSet rs=null;//结果数据集
  22.  
  23. private static BasicDataSource ds=null;
  24.  
  25. //BasicDataSource对象的相关初始化
  26. public static void jdcpInit(){
  27. ds=new BasicDataSource();//创建BasicDataSource对象
  28. ds.setUrl(url);
  29. ds.setDriverClassName(driverClassName);
  30. ds.setUsername(username);
  31. ds.setPassword(password);
  32. ds.setMaxIdle(2);//设置连接池中存在的最大连接对象的数量为2个
  33. }
  34.  
  35. public static void main(String[] args) {
  36. jdcpInit();
  37. try {
  38. conn=ds.getConnection();//从BasicDataSource对象中获取数据库连接
  39. //一下的操作就和JDBC相同了
  40. stat=conn.createStatement();
  41. rs=stat.executeQuery("select * from roster");
  42. while(rs.next())
  43. System.out.println("name:"+rs.getString("name"));
  44. } catch (SQLException e) {
  45. e.printStackTrace();
  46. }finally{
  47. try {
  48. if(rs!=null)
  49. rs.close();
  50. if(stat!=null)
  51. stat.close();
  52. if(conn!=null)
  53. conn.close();
  54. //释放数据库连接,这里连接池重写了JDBC中数据库连接(connection对象)的close()方法,原来是销毁,现在是归还给连接池,以供下个线程调用
  55. } catch (SQLException e) {
  56. e.printStackTrace();
  57. }
  58.  
  59. }
  60.  
  61. }
  62.  
  63. }

数据库连接池(基于MySQL数据库)的更多相关文章

  1. Myeclipse WEB工程JSP使用JNDI 数据库连接池连接Mysql数据库

    在网上查了很多,最后实现了.下面写一下过程: 首先,在WEBROOT/META-INF下建一个文件context.xml,内容为: <?xml version="1.0" e ...

  2. python通过数据库连接池实现mysql数据库增删改查

    import pymysql from DBUtils.PooledDB import PooledDB class SQLHandler(object): def __init__(self, ho ...

  3. mysql数据库连接池使用(三)数据库元数据信息反射数据库获取数据库信息

    1.1. mysql数据库连接池使用(三)数据库元数据信息反射数据库获取数据库信息 有时候我们想要获取到数据库的基本信息,当前程序连接的那个数据库,数据库的版本信息,数据库中有哪些表,表中都有什么字段 ...

  4. 在Jena框架下基于MySQL数据库实现本体的存取操作

    在Jena框架下基于MySQL数据库实现本体的存取操作 转自:http://blog.csdn.net/jtz_mpp/article/details/6224311 最近在做一个基于本体的管理系统. ...

  5. 解决数据库连接池连接mysql时,每隔8小时mysql自动断开所有连接的问题

    解决数据库连接池连接mysql时,每隔8小时mysql自动断开所有连接的问题 最近有个问题非常讨厌,我们的工程中使用自己的连接池连接mysql数据库,可mysql数据库每隔8小时就会自动断开所有链接, ...

  6. 基于Mysql数据库亿级数据下的分库分表方案

    移动互联网时代,海量的用户数据每天都在产生,基于用户使用数据的用户行为分析等这样的分析,都需要依靠数据都统计和分析,当数据量小时,问题没有暴露出来,数据库方面的优化显得不太重要,一旦数据量越来越大时, ...

  7. canal 基于Mysql数据库增量日志解析

    canal 基于Mysql数据库增量日志解析  1.前言  最近太多事情 工作的事情,以及终身大事等等 耽误更新,由于最近做项目需要同步监听 未来电视 mysql的变更了解到公司会用canal做增量监 ...

  8. 二、spring Boot构建的Web应用中,基于MySQL数据库的几种数据库连接方式进行介绍

    包括JDBC.JPA.MyBatis.多数据源和事务. 一.JDBC 连接数据库 1.属性配置文件(application.properties) spring.datasource.url=jdbc ...

  9. python数据库连接池基于DBUtils

    DBUtils模块的使用的两种方式 DBUtils是Python的一个用于实现数据库连接池的模块 安装 pip install DBUtils 1.使用姿势一(不建议此方法) 为每个线程 (资源占用过 ...

随机推荐

  1. PowerShell 实现批量下载文件

    简介 批量文件下载器 PowerShell 版,类似于迅雷批量下载功能,且可以破解 Referer 防盗链 源代码 [int]$script:completed = 0 # 下载完成数量 [int]$ ...

  2. Scala - 快速学习03 - 基础语法

    1- 变量 变量 mutable variable 在程序运行过程中其值可能发生改变的量 关键词var定义变量,定义时直接进行求值 常量 immutable variable 在程序运行过程中其值不会 ...

  3. Python - 网络爬虫(Web Scraping)

    专栏 从零开始写Python爬虫:https://zhuanlan.zhihu.com/Ehco-python requests库的安装与使用:http://t.cn/RTuUuf7 BS4库的安装与 ...

  4. 一文了解Python中的循环(for while break continue 嵌套循环...)

    循环 目标 程序的三大流程 while 循环基本使用 break 和 continue while 循环嵌套 01. 程序的三大流程 在程序开发中,一共有三种流程方式: 顺序 —— 从上向下,顺序执行 ...

  5. H5拖动实现代码

    原理以后有空再说现在嘛先上代码.... ;} html,body { width: 100%; height: 100%; ; } #dragBoxContainer{ width: 150px; p ...

  6. 十大经典排序算法(python实现)(原创)

    个人最喜欢的排序方法是非比较类的计数排序,简单粗暴.专治花里胡哨!!! 使用场景: 1,空间复杂度 越低越好.n值较大: 堆排序 O(nlog2n) O(1) 2,无空间复杂度要求.n值较大: 桶排序 ...

  7. sql server 索引阐述系列八 统计信息

    一.概述 sql server在快速查询值时只有索引还不够,还需要知道操作要处理的数据量有多少,从而估算出复杂度,选择一个代价小的执行计划,这样sql server就知道了数据的分布情况.索引的统计值 ...

  8. leetcode — plus-one

    import java.util.ArrayList; import java.util.Arrays; import java.util.List; /** * Source : https://o ...

  9. CentOS docker 常用命令

    yum install docker 安装服务 systemctl start docker.service 启动服务 systemctl enable docker.service 开机启动服务 d ...

  10. TensorFlow中的并行执行引擎——StreamExecutor框架

    背景 [作者:DeepLearningStack,阿里巴巴算法工程师,开源TensorFlow Contributor] 在前一篇文章中,我们梳理了TensorFlow中各种异构Device的添加和注 ...