我必须处理很多文件。我编写了简单的Java程序来完成这项工作,但速度太慢了。
我需要超过1个工作线程。
我是Java和Java多线程的新手。
这是我的代码(简化):
public static void main(String[] args)
{
// some queue here?
for (int i = 1; i < 8000000; i++)
{
processId(i);
}
}
public static void processId(int id)
{
try
{
// do work
System.out.println("Im working on: " + Integer.toString(id));
}
catch (Exception e)
{
// do something with errors
System.out.println("Error while working on: " + Integer.toString(id));
}
}
如何添加8个线程的简单队列?
答案 0 :(得分:2)
你应该研究执行者。
您可以使用以下方法创建8个线程的线程池:
ExecutorService executor = Executors.newFixedThreadPool(8);
然后按照以下方式在循环中提交您的任务:
final int finalId = i; // final is necessary to be enclosed in lambda
executor.submit(() -> processId(finalId));
或者在Java 8之前:
final int temp = i; // final is necessary to be enclosed in anonymous class
executor.submit(new Runnable() {
public void run() {
processId(finalId);
}
});
如上所述in the documentation,如果不再需要,请不要忘记关闭线程池。以下是doc中的示例:
private void shutdownAndAwaitTermination(ExecutorService pool) {
pool.shutdown(); // Disable new tasks from being submitted
try {
// Wait a while for existing tasks to terminate
if (!pool.awaitTermination(60, TimeUnit.SECONDS)) {
pool.shutdownNow(); // Cancel currently executing tasks
// Wait a while for tasks to respond to being cancelled
if (!pool.awaitTermination(60, TimeUnit.SECONDS))
System.err.println("Pool did not terminate");
}
} catch (InterruptedException ie) {
// (Re-)Cancel if current thread also interrupted
pool.shutdownNow();
// Preserve interrupt status
Thread.currentThread().interrupt();
}
}
答案 1 :(得分:2)
您应该查看ExecutorService
。这将使多线程变得容易。一个例子:
主要代码:
ExecutorService pool = Executors.newFixedThreadPool(8);
for (int i = 1; i < 8000000; i++) {
pool.submit(new intProcessingTask(i));
}
pool.shutdown();
pool.awaitTermination(Long.MAX_VALUE, TimeUnit.MILLISECONDS);
// all tasks have now finished (unless an exception is thrown above)
intProcessingTask
代码:
private static class DownloadTask implements Runnable {
private int id;
public DownloadTask(int id) {
this.id = id;
}
@Override
public void run() {
System.out.println("Im working on: " + Integer.toString(id));
}
}
这比其他答案略长,但几乎完全相同,适用于Java 7及更早版本。
答案 2 :(得分:2)
Java有许多方法可以处理多线程。根据您的问题,您需要一个队列,我认为最简单的版本是使用Java ExecutorService
。你可以看到这段代码:
public static void main(String[] args) {
// creating a thread pool with maximum thread will be 8
ExecutorService executorService = Executors.newFixedThreadPool(8);
for (int i = 0; i < 8000000; i++) {
final int threadId = i;
executorService.execute(new Runnable() {
public void run() {
processId(threadId);
}
});
}
}
ExecutorService
有一些方法:
我建议您查看此链接:ExecutorService tutorial以获得明确说明。
希望这有帮助:)