Mysql连接池解决并发问题

/**
  * 连接池类
  */
package com.junones.test;
 
import java.sql.Connection;
import java.sql.SQLException;
import java.util.HashMap;
import java.util.Map;
import java.util.Map.Entry;
 
import com.mysql.jdbc.jdbc2.optional.MysqlDataSource;
 
public class MySQLPool {
     private static volatile MySQLPool pool;
     private MysqlDataSource ds;
     private Map<Connection, Boolean> map;
  
     private String url = "jdbc:mysql://localhost:3306/test" ;
     private String username = "root" ;
     private String password = "root1234" ;
     private int initPoolSize = 10 ;
     private int maxPoolSize = 200 ;
     private int waitTime = 100 ;
     
     private MySQLPool() {
         init();
     }
     
     public static MySQLPool getInstance() {
         if (pool == null ) {
             synchronized (MySQLPool. class ) {
                 if (pool == null ) {
                     pool = new MySQLPool();
                 }
             }
         }
         return pool;
     }
     
     private void init() {
         try {
             ds = new MysqlDataSource();
             ds.setUrl(url);
             ds.setUser(username);
             ds.setPassword(password);
             ds.setCacheCallableStmts( true );
             ds.setConnectTimeout( 1000 );
             ds.setLoginTimeout( 2000 );
             ds.setUseUnicode( true );
             ds.setEncoding( "UTF-8" );
             ds.setZeroDateTimeBehavior( "convertToNull" );
             ds.setMaxReconnects( 5 );
             ds.setAutoReconnect( true );
             map = new HashMap<Connection, Boolean>();
             for ( int i = 0 ; i < initPoolSize; i++) {
                 map.put(getNewConnection(), true );
             }
         } catch (Exception e) {
             e.printStackTrace();
         }
     }
     
     public Connection getNewConnection() {
         try {
             return ds.getConnection();
         } catch (SQLException e) {
             e.printStackTrace();
         }
         return null ;
     }
     
     public synchronized Connection getConnection() {
         Connection conn = null ;
         try {
             for (Entry<Connection, Boolean> entry : map.entrySet()) {
                 if (entry.getValue()) {
                     conn = entry.getKey();
                     map.put(conn, false );
                     break ;
                 }
             }
             if (conn == null ) {
                 if (map.size() < maxPoolSize) {
                     conn = getNewConnection();
                     map.put(conn, false );
                 } else {
                     wait(waitTime);
                     conn = getConnection();
                 }
             }
         } catch (Exception e) {
             e.printStackTrace();
         }
         return conn;
     }
     
     public void releaseConnection(Connection conn) {
         if (conn == null ) {
             return ;
         }
         try {
             if (map.containsKey(conn)) {
                 if (conn.isClosed()) {
                     map.remove(conn);
                 } else {
                     if (!conn.getAutoCommit()) {
                         conn.setAutoCommit( true );
                     }
                     map.put(conn, true );
                 }
             } else {
                 conn.close();
             }
         } catch (SQLException e) {
             e.printStackTrace();
         }
     }
}
 
/**
  * 测试类
  */
package com.junones.test;
 
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
 
public class TestMySQLPool {
     private static volatile int a;
 
     private synchronized static void incr() {
         a++;
     }
 
     public static void main(String[] args) throws InterruptedException {
         int times = 10000 ;
         long start = System.currentTimeMillis();
         for ( int i = 0 ; i < times; i++) {
             new Thread( new Runnable() {
 
                 @Override
                 public void run() {
 
                     MySQLPool pool = MySQLPool.getInstance();
                     Connection conn = pool.getConnection();
                     Statement stmt = null ;
                     ResultSet rs = null ;
                     try {
                         stmt = conn.createStatement();
                         rs = stmt.executeQuery( "select id, name from t_test" );
                         while (rs.next()) {
                             System.out.println(rs.getInt( 1 ) + ", "
                                     + rs.getString( 2 ));
                         }
                     } catch (SQLException e) {
                         e.printStackTrace();
                     } finally {
                         incr();
                         if (rs != null ) {
                             try {
                                 rs.close();
                             } catch (SQLException e) {
                                 e.printStackTrace();
                             }
                         }
                         if (stmt != null ) {
                             try {
                                 stmt.close();
                             } catch (SQLException e) {
                             }
                         }
                         pool.releaseConnection(conn);
                     }
                 }
             }).start();
         }
         while ( true ) {
             if (a == times) {
                 System.out.println( "finished, time:"
                         + (System.currentTimeMillis() - start));
                 break ;
             }
             Thread.sleep( 100 );
         }
     }
}
 
测试结果: 1 万个并发, 5 秒完成。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值