设为首页 收藏本站
查看: 1409|回复: 0

[经验分享] JDBC 数据库连接池 小结

[复制链接]

尚未签到

发表于 2017-2-19 09:17:46 | 显示全部楼层 |阅读模式
  当对数据库的访问不是很频繁时,可以在每次访问数据库时建立一个连接,用完之后关闭。但是,对于一个复杂的数据库应用,频繁的建立、关闭连接,会极大的减低系统性能,造成瓶颈。所以可以使用数据库连接池来达到连接资源的共享,使得对于数据库的连接可以使高效、安全的复用。
  1.通过一个小测试来了解数据库连接池的原理
  (1)创建一个属性文件  dbpool.properties



1 driverClassName=com.mysql.jdbc.Driver
2 username=root
3 password=iloveyou
4 url=jdbc:mysql://localhost:3306/student
5 poolSize=5
  (2)创建实现数据库连接池的类文件  ConnectionPool.java


DSC0000.gif DSC0001.gif ConnectionPool.java


  1 package dbpool;
  2
  3 import java.io.FileInputStream;
  4 import java.io.FileNotFoundException;
  5 import java.io.IOException;
  6 import java.sql.Connection;
  7 import java.sql.SQLException;
  8 import java.util.Properties;
  9 import java.util.Vector;
10
11 public class ConnectionPool {
12     private Vector<Connection> pool;
13     private String url;
14     private String username;
15     private String password;
16     private String driverClassName;
17     private int poolSize = 1;
18     private static ConnectionPool instance = null;
19     
20     //私有构造方法,禁止外部创建本类的对象,要想获得本类的对象,通过<code>getInstance</code>方法
21     private ConnectionPool(){
22         System.out.println("构造函数");
23         init();
24     }
25     
26     //连接池初始化方法,读取属性文件的内容,建立连接池中的初始连接
27     private void init(){
28         readConfig();
29         pool = new Vector<Connection>(poolSize);
30         addConnection();
31     }
32     
33     //返回连接到连接池中
34     public synchronized void release(Connection coon){
35         pool.add(coon);
36     }
37     
38     //关闭连接池中的所有数据库连接
39     public synchronized void closePool(){
40         for (int i = 0; i < pool.size(); i++) {
41             try {
42                 ((Connection)pool.get(i)).close();
43             } catch (SQLException e) {
44                 // TODO Auto-generated catch block
45                 e.printStackTrace();
46             }
47             pool.remove(i);
48         }
49     }
50     
51     //返回当前连接池的一个对象
52     public static ConnectionPool getInstance(){
53         if (instance == null) {
54             instance = new ConnectionPool();
55         }
56         return instance;
57     }
58     
59     //返回连接池中的一个数据库连接
60     public synchronized Connection getConnection(){
61         if (pool.size() > 0) {
62             Connection conn = pool.get(0);
63             pool.remove(conn);
64             return conn;
65         }else {
66             return null;
67         }
68     }
69     
70     //在连接池中创建初始设置的数据库连接
71     private void addConnection(){
72         Connection coon = null;
73         for (int i = 0; i < poolSize; i++) {
74             try {
75                 Class.forName(driverClassName);
76                 coon = java.sql.DriverManager.getConnection(url, username, password);
77                 pool.add(coon);
78             } catch (ClassNotFoundException e) {
79                 // TODO Auto-generated catch block
80                 e.printStackTrace();
81             } catch (SQLException e) {
82                 // TODO Auto-generated catch block
83                 e.printStackTrace();
84             }
85         }
86     }
87     
88     //读取设置连接池的属性文件
89     private void readConfig(){
90         try {
91             String path = System.getProperty("user.dir") + "\\dbpool.properties";
92             FileInputStream is = new FileInputStream(path);
93             Properties props = new Properties();
94             props.load(is);
95             this.driverClassName = props.getProperty("driverClassName");
96             this.username = props.getProperty("username");
97             this.password = props.getProperty("password");
98             this.url = props.getProperty("url");
99             this.poolSize = Integer.parseInt(props.getProperty("poolSize"));
100         } catch (FileNotFoundException e) {
101             // TODO Auto-generated catch block
102             e.printStackTrace();
103             System.err.println("属性文件找不到");
104         } catch (IOException e) {
105             // TODO Auto-generated catch block
106             e.printStackTrace();
107             System.err.println("读取属性文件出错");
108         }
109     }
110     
111 }
  (3)创建一个使用连接池访问数据库的类文件  ConnectionPoolTest.java


ConnectionPoolTest.java


1 package dbpool;
2
3 import java.sql.Connection;
4 import java.sql.PreparedStatement;
5 import java.sql.ResultSet;
6 import java.sql.SQLException;
7
8 public class ConnectionPoolTest {
9     public static void main(String[] args) throws SQLException{
10         String sql = "select * from user";
11         ConnectionPool pool = null;
12         
13         for (int i = 0; i < 2; i++) {
14             pool = ConnectionPool.getInstance();
15             Connection conn = pool.getConnection();
16             PreparedStatement stmt = conn.prepareStatement(sql);
17             ResultSet rs = stmt.executeQuery(sql);
18             while (rs.next()) {
19                 System.out.println(rs.getString(1) + "\t\t" + rs.getString(2) + "\t\t" + rs.getString(3));
20             }
21             rs.close();
22             stmt.close();
23             pool.release(conn);
24         }
25         pool.closePool();
26     }
27 }
  2.在开发具体项目时没有必要自己编写数据库连接池,现在已经有很多现成的组件。许多服务器已经内置了数据库连接池,如Tomcat服务器、Jboss服务器和WebLogic服务器等。我自己根据书上的例子,配置了一下Tomcat服务器。配置步骤如下:
  (1)配置Tomcat根目录下的 \conf 中的文件 context.xml 如下:



1 <!--Resource 设置数据库连接池的核心-->
2     <!--属性 name 数据源的名字       属性 auth 表示验证方式     type 资源的类型       -->
3     <Resource name="jdbc/DBWater" auth="Container" Type="javax.sql.DataSource"
4               maxActive="100" maxIdle="30" maxWait="10000"
5               username="root" password="*******"
6               driverClassName="com.mysql.jdbc.Driver"
7               url="jdbc:mysql://localhost:3306/student"/>
  将这段代码添加到<context></context>之间
  (2)修改项目工程目录下 WebRoot/WEB-INF/web.xml 文件:



1 <resource-ref>
2   <!-- 描述信息 -->
3   <description>Connection Pool</description>
4   <!-- 数据源名字 和上面配置中数据源的名字一致-->
5   <res-ref-name>jdbc/DBWater</res-ref-name>
6   <!-- 数据源类型 -->
7   <res-type>javax.sql.DataSource</res-type>
8   <res-auth>Container</res-auth>
9   <res-sharing-scope>Shareable</res-sharing-scope>
10 </resource-ref>
  下面就可以进行连接池使用了。比如,这里,创建一个DBWater.java文件:


DBWater.java


1 package com.lihui.dbwater;
2
3 import java.sql.Connection;
4 import java.sql.ResultSet;
5 import java.sql.Statement;
6
7 import javax.naming.Context;
8 import javax.naming.InitialContext;
9 import javax.naming.NamingException;
10 import javax.sql.DataSource;
11
12 public class DBWater {
13     String userId;
14     String name;
15     String password;
16     
17     public String getUserId(){
18         return userId;
19     }
20     
21     public String getName(){
22         return name;
23     }
24     
25     public String getpassword(){
26         return password;
27     }
28     
29     public void init(){
30         try {
31             InitialContext initC = new InitialContext();//创建InitialContext对象
32             if (initC == null) {
33                 throw new Exception("No Context");
34             }
35             Context context = (Context)initC.lookup("java:comp/env");//不变
36             DataSource ds = (DataSource)context.lookup("jdbc/DBWater");//tomcat服务器配置文件中数据源名称
37             if (ds != null) {
38                 Connection conn = ds.getConnection();
39                 if (conn != null) {
40                     Statement statement = conn.createStatement();
41                     ResultSet resultSet = statement.executeQuery("select * from user");
42                     while (resultSet.next()) {
43                         userId = resultSet.getString(1);
44                         name = resultSet.getString(2);
45                         password = resultSet.getString(3);
46                     }
47                     conn.close();
48                 }
49             }
50         } catch (NamingException e) {
51             // TODO Auto-generated catch block
52             e.printStackTrace();
53         } catch (Exception e) {
54             // TODO Auto-generated catch block
55             e.printStackTrace();
56         }
57     }
58 }
  那么在jsp文件中调用该类:



1 <%@ page language="java" import="java.util.*" pageEncoding="gb2312"%>
2 <%@page import="com.lihui.dbwater.DBWater"%>
3
4 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
5 <html>
6   <head>
7     <title>连接池测试</title>
8   </head>
9   
10   <body>
11   <%
12       DBWater rs = new DBWater();
13       rs.init();
14 %>
15   id:<%=rs.getUserId() %>
16   name:<%=rs.getName() %>
17   psd:<%=rs.getpassword() %>
18   </body>
19 </html>
  

运维网声明 1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com

所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其承担任何法律责任,如涉及侵犯版权等问题,请您及时通知我们,我们将立即处理,联系人Email:kefu@iyunv.com,QQ:1061981298 本贴地址:https://www.yunweiku.com/thread-344080-1-1.html 上篇帖子: 数据源相关概念 下篇帖子: java项目路径 文件路径 相对路径 整理
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

扫码加入运维网微信交流群X

扫码加入运维网微信交流群

扫描二维码加入运维网微信交流群,最新一手资源尽在官方微信交流群!快快加入我们吧...

扫描微信二维码查看详情

客服E-mail:kefu@iyunv.com 客服QQ:1061981298


QQ群⑦:运维网交流群⑦ QQ群⑧:运维网交流群⑧ k8s群:运维网kubernetes交流群


提醒:禁止发布任何违反国家法律、法规的言论与图片等内容;本站内容均来自个人观点与网络等信息,非本站认同之观点.


本站大部分资源是网友从网上搜集分享而来,其版权均归原作者及其网站所有,我们尊重他人的合法权益,如有内容侵犯您的合法权益,请及时与我们联系进行核实删除!



合作伙伴: 青云cloud

快速回复 返回顶部 返回列表