解决:抱歉,问题与Java线程无关。 C3P0的ComboPooledDataSource正在创建如此多的线程而不是释放它们。切换到DBCP2的BasicDataSource后,线程数不再增加。
我写了一个网络应用程序,因为无法创建更多线程而崩溃。在其中一个函数中,我让ExecutorService
创建一个包含10个线程的线程池作为该函数的局部变量。当我监视线程时,每次调用该函数时,都会创建大约12个线程。
然后我将其移动到测试文件并在多个shell中运行:
public static void main(String[] args) throws Exception {
testRun();
Thread.sleep(1253234234);
}
public static testRun() {
WorkQueue queue = new ThreadPool(10);
for (int i = 0; i < 10; i++) {
queue.addJob(new Runnable() {
@Override
public void run() {
System.out.println(this);
try {
Thread.sleep(5000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}});
}
queue.startJobs();
queue.wait(10);
}
public void wait(int seconds) {
executor.shutdown();
try {
if (!executor.awaitTermination(seconds, TimeUnit.SECONDS)) {
throw new RuntimeException("Thread pool terminated unexpectedly due to time out.");
}
} catch (InterruptedException ie) {
throw new RuntimeException("Thread interrupt event is received while waiting for termination of ThreadPool - " + ie.getMessage());
}
}
这会在每个shell中创建25个线程,然后在完成后仅释放10个线程。因此,每次调用此函数时,都有15个线程未被释放。我猜测15是maxPoolSize,10是corePoolSize。但是为什么在功能结束时它们都不会被释放?
所以我想也许我不理解这个ExecutorService
类并编写原始线程:
public static void main(String[] args) throws Exception {
testRun();
Thread.sleep(1253234234);
}
private static void testRun() throws Exception {
for (int i = 0; i < 10; i++) {
Thread t = new Thread(new Runnable() {
@Override
public void run() {
try {
Thread.sleep(5000);
System.out.println(this);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
});
t.start();
}
}
这些现在为每个shell创建27个线程,并在每个函数完成后释放10个。我究竟做错了什么?如何在函数本地释放这些线程?有人能指出我正确的方式吗?
请在测试后替换测试内容时忽略编译/语法错误,因此不会复制并粘贴工作代码。
谢谢。