gpt4 book ai didi

java - 使用 H2 数据库了解 JdbcConnectionPool

转载 作者:搜寻专家 更新时间:2023-10-31 20:27:54 25 4
gpt4 key购买 nike

我有一个 H2 服务器进程在我的主服务器机器上运行,允许 TCP 连接。

假设我要执行 100 个 SQL 查询:

SELECT * FROM TEST

并且,出于我自己的目的,我想对每个线程执行一个查询。让我们用一个且只有一个在线程间共享的 Connection 对象来做到这一点:

  • 创建一个 Connection 对象。
  • 创建 100 个线程。
  • 在每个线程中,使用共享的Connection 对象调用SQL 查询。

上面的方法可以工作,但会有点慢。当然,毕竟,如果有人正在使用一个Connection,那么其他人就得等待了。

那么,让我们为每个线程创建一个Connection:

  • 创建 100 个线程。
  • 在每个线程中,创建一个新的Connection 对象并调用SQL 查询。

快得多。但是感觉100个连接有点浪费。也许 50 个连接就可以了。我听说我可以使用 JdbcConnectionPool 来做这类事情。

  • 创建一个最多有 50 个连接的 JdbcConnectionPool
  • 创建 100 个线程。
  • 在每个线程中,使用 pool.getConnection() 然后调用 SQL 查询。

嗯。它很慢。如果有的话,它和第一种方法一样慢。也许,出于好奇,我应该将最大连接数设置为 100...

...它仍然很慢。诡异的。据我了解,一个有 100 个连接的池相当于为我的 100 个线程中的每一个创建一个连接。

可能是什么问题?这是最后一次测试的代码:

import java.sql.Connection;
import java.sql.ResultSet;

import org.h2.jdbcx.JdbcConnectionPool;

public class App {

public static void main(String[] args) throws Exception {
Class.forName("org.h2.Driver");
JdbcConnectionPool pool = JdbcConnectionPool.create("url", "user", "password");
pool.setMaxConnections(100);
for (int i = 0; i < 100; ++i) {
Thread t = new Thread(new Client(i, pool));
t.start();
}
}
}

class Client implements Runnable {
int id;
JdbcConnectionPool pool;
public Client(int id, JdbcConnectionPool pool) {
this.id = id;
this.pool = pool;
}
public void run() {
try {
Connection conn = pool.getConnection();
ResultSet set = conn.createStatement().executeQuery("SELECT * FROM TEST");
if (set.next()) {
System.out.println("Finished " + id);
}
set.close();
conn.close();
}catch (Exception e) {

}
}
}

我正在使用 H2 1.4.182

最佳答案

JdbcConnectionPool#getConnection()源码:

  public Connection getConnection() throws SQLException {
long max = System.currentTimeMillis() + timeout * 1000;
do {
synchronized (this){
if (activeConnections < maxConnections) {
return getConnectionNow();
}
try {
wait(1000);
} catch (InterruptedException e) {
// ignore
}
}
} while (System.currentTimeMillis() <= max);
throw new SQLException("Login timeout", "08001", 8001);
}

您的示例中最昂贵的操作之一是创建连接。如您所见,方法 getConnection() 具有锁 synchronized (this) 因此只有一个线程可以同时创建连接,所有其他线程都在等待。

我相信内置的 h2 连接池非常简单。如果你想拥有高性能的连接池,你可以看看 C3P0 或 BoneCP。

关于java - 使用 H2 数据库了解 JdbcConnectionPool,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27069093/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com