ThreadPoolExecutor的execute()和submit()方法
我希望使用多线程执行一个运算,并且线程执行完毕后我要获取执行结果。其实使用线程池ThreadPoolExecutor的execute()和submit()方法都可以。
使用execute()的话,事先定义一个存放返回结果的集合,开辟线程时,将集合的元素作为参数代入自定义的Runnable接口的实现类中,多线程执行完毕后遍历集合即可获得运算结果。
使用submit()的话,可以在submit()中执行一个Callable接口的实现类,submit()方法可以返回一个Future<> future,然后使用future.get()方法获得返回结果,由于future.get()会使调用线程池的线程阻塞,等待返回结果,所以可以先将Future<> future放入一个集合,等多线程执行完毕后再遍历集合获得运算结果。
使用execute()方法:
定义一个结果类:
-
public class RunResult {
-
// 输入参数
-
private Integer param;
-
// 是否运算成功
-
private Boolean success;
-
// 运算结果
-
private Integer result;
-
public Integer getParam() {
-
return param;
-
}
-
public void setParam(Integer param) {
-
this.param = param;
-
}
-
public Boolean getSuccess() {
-
return success;
-
}
-
public void setSuccess(Boolean success) {
-
this.success = success;
-
}
-
public Integer getResult() {
-
return result;
-
}
-
public void setResult(Integer result) {
-
this.result = result;
-
}
-
}
定义一个Runnable接口的实现类:
-
public class MyRunnable implements Runnable {
-
// 运算结果类
-
private RunResult result;
-
// 线程同步器
-
private CountDownLatch main;
-
-
public void run() {
-
String name = Thread.currentThread().getName();
-
System.out.println(name + " 线程开始执行" + "-" + result.getParam());
-
for (int i = 0; i < 1; i++) {
-
for (int j = 1; j <= 200000000; j++) {
-
if (j == 200000000 && null != result.getParam()) {
-
result.setResult(result.getParam()*10);
-
result.setSuccess(true);
-
System.out.println(name + " 线程正在进行计算" + "-" + result.getParam());
-
} else {
-
result.setSuccess(false);
-
}
-
}
-
}
-
System.out.println(name + " 线程执行完毕" + "-" + result.getParam());
-
main.countDown();
-
}
-
public MyRunnable(RunResult result, CountDownLatch main) {
-
super();
-
this.result = result;
-
this.main = main;
-
}
-
public MyRunnable() {
-
super();
-
}
-
}
main方法:
-
public static void main(String[] args) {
-
ThreadPoolExecutor threadPool = new ThreadPoolExecutor(6, 10, 10L, TimeUnit.SECONDS,
-
new LinkedBlockingQueue<Runnable>(20),
-
Executors.defaultThreadFactory(),
-
new ThreadPoolExecutor.CallerRunsPolicy());
-
// 存放结果类的集合
-
List<RunResult> list = new ArrayList<RunResult>(12);
-
// 线程同步器
-
CountDownLatch main = new CountDownLatch(12);
-
for (int i = 1; i <= 12; i++) {
-
RunResult result = new RunResult();
-
result.setParam(i);
-
list.add(result);
-
MyRunnable runnable = new MyRunnable(result,main);
-
threadPool.execute(runnable);
-
}
-
try {
-
main.await();
-
System.out.println(JSON.toJSON(list));
-
// 线程池不用了,关闭线程池
-
threadPool.shutdown();
-
//threadPool.shutdownNow();
-
} catch (InterruptedException e) {
-
-
}
-
}
执行结果:
-
pool-1-thread-1 线程开始执行-1
-
pool-1-thread-5 线程开始执行-5
-
pool-1-thread-3 线程开始执行-3
-
pool-1-thread-2 线程开始执行-2
-
pool-1-thread-4 线程开始执行-4
-
pool-1-thread-6 线程开始执行-6
-
pool-1-thread-1 线程正在进行计算-1
-
pool-1-thread-1 线程执行完毕-1
-
pool-1-thread-1 线程开始执行-7
-
pool-1-thread-6 线程正在进行计算-6
-
pool-1-thread-6 线程执行完毕-6
-
pool-1-thread-6 线程开始执行-8
-
pool-1-thread-5 线程正在进行计算-5
-
pool-1-thread-5 线程执行完毕-5
-
pool-1-thread-5 线程开始执行-9
-
pool-1-thread-3 线程正在进行计算-3
-
pool-1-thread-3 线程执行完毕-3
-
pool-1-thread-3 线程开始执行-10
-
pool-1-thread-4 线程正在进行计算-4
-
pool-1-thread-4 线程执行完毕-4
-
pool-1-thread-4 线程开始执行-11
-
pool-1-thread-2 线程正在进行计算-2
-
pool-1-thread-2 线程执行完毕-2
-
pool-1-thread-2 线程开始执行-12
-
pool-1-thread-5 线程正在进行计算-9
-
pool-1-thread-5 线程执行完毕-9
-
pool-1-thread-4 线程正在进行计算-11
-
pool-1-thread-4 线程执行完毕-11
-
pool-1-thread-2 线程正在进行计算-12
-
pool-1-thread-2 线程执行完毕-12
-
pool-1-thread-6 线程正在进行计算-8
-
pool-1-thread-3 线程正在进行计算-10
-
pool-1-thread-3 线程执行完毕-10
-
pool-1-thread-1 线程正在进行计算-7
-
pool-1-thread-6 线程执行完毕-8
-
pool-1-thread-1 线程执行完毕-7
-
[{"result":10,"param":1,"success":true},{"result":20,"param":2,"success":true},{"result":30,"param":3,"success":true},{"result":40,"param":4,"success":true},{"result":50,"param":5,"success":true},{"result":60,"param":6,"success":true},{"result":70,"param":7,"success":true},{"result":80,"param":8,"success":true},{"result":90,"param":9,"success":true},{"result":100,"param":10,"success":true},{"result":110,"param":11,"success":true},{"result":120,"param":12,"success":true}]
使用submit()方法:
返回结果类同上
定义一个Callable接口的实现类:
-
public class MyCallable implements Callable<RunResult> {
-
// 运算结果类
-
private RunResult result;
-
// 线程同步器
-
private CountDownLatch main;
-
-
public RunResult call() throws Exception {
-
String name = Thread.currentThread().getName();
-
System.out.println(name + " 线程开始执行" + "-" + result.getParam());
-
for (int i = 0; i < 1; i++) {
-
for (int j = 1; j <= 200000000; j++) {
-
if (j == 200000000 && null != result.getParam()) {
-
result.setResult(result.getParam()*10);
-
result.setSuccess(true);
-
System.out.println(name + " 线程正在进行计算" + "-" + result.getParam());
-
} else {
-
result.setSuccess(false);
-
}
-
}
-
}
-
System.out.println(name + " 线程执行完毕" + "-" + result.getParam());
-
main.countDown();
-
return result;
-
}
-
public MyCallable(RunResult result, CountDownLatch main) {
-
super();
-
this.result = result;
-
this.main = main;
-
}
-
public MyCallable() {
-
super();
-
}
-
}
main方法:
-
public static void main(String[] args) {
-
ThreadPoolExecutor threadPool = new ThreadPoolExecutor(6, 10, 10L, TimeUnit.SECONDS,
-
new LinkedBlockingQueue<Runnable>(20),
-
Executors.defaultThreadFactory(),
-
new ThreadPoolExecutor.CallerRunsPolicy());
-
// 存放Future<>的集合
-
List<Future<RunResult>> list = new ArrayList<Future<RunResult>>(12);
-
// 线程同步器
-
CountDownLatch main = new CountDownLatch(12);
-
for (int i = 1; i <= 12; i++) {
-
RunResult result = new RunResult();
-
result.setParam(i);
-
MyCallable callable = new MyCallable(result,main);
-
Future<RunResult> runResultFuture = threadPool.submit(callable);
-
list.add(runResultFuture);
-
}
-
try {
-
main.await();
-
for (int i = 0; i < list.size(); i++) {
-
RunResult runResult = list.get(i).get();
-
System.out.println(JSON.toJSON(runResult));
-
}
-
// 线程池不用了,关闭线程池
-
threadPool.shutdown();
-
//threadPool.shutdownNow();
-
} catch (InterruptedException e) {
-
-
} catch (ExecutionException e) {
-
-
}
-
}
执行结果:
-
pool-1-thread-3 线程开始执行-3
-
pool-1-thread-4 线程开始执行-4
-
pool-1-thread-2 线程开始执行-2
-
pool-1-thread-1 线程开始执行-1
-
pool-1-thread-5 线程开始执行-5
-
pool-1-thread-6 线程开始执行-6
-
pool-1-thread-1 线程正在进行计算-1
-
pool-1-thread-3 线程正在进行计算-3
-
pool-1-thread-5 线程正在进行计算-5
-
pool-1-thread-5 线程执行完毕-5
-
pool-1-thread-2 线程正在进行计算-2
-
pool-1-thread-2 线程执行完毕-2
-
pool-1-thread-6 线程正在进行计算-6
-
pool-1-thread-6 线程执行完毕-6
-
pool-1-thread-4 线程正在进行计算-4
-
pool-1-thread-4 线程执行完毕-4
-
pool-1-thread-6 线程开始执行-9
-
pool-1-thread-5 线程开始执行-7
-
pool-1-thread-2 线程开始执行-8
-
pool-1-thread-3 线程执行完毕-3
-
pool-1-thread-3 线程开始执行-11
-
pool-1-thread-1 线程执行完毕-1
-
pool-1-thread-1 线程开始执行-12
-
pool-1-thread-4 线程开始执行-10
-
pool-1-thread-6 线程正在进行计算-9
-
pool-1-thread-5 线程正在进行计算-7
-
pool-1-thread-5 线程执行完毕-7
-
pool-1-thread-1 线程正在进行计算-12
-
pool-1-thread-1 线程执行完毕-12
-
pool-1-thread-4 线程正在进行计算-10
-
pool-1-thread-2 线程正在进行计算-8
-
pool-1-thread-3 线程正在进行计算-11
-
pool-1-thread-6 线程执行完毕-9
-
pool-1-thread-3 线程执行完毕-11
-
pool-1-thread-2 线程执行完毕-8
-
pool-1-thread-4 线程执行完毕-10
-
{"result":10,"param":1,"success":true}
-
{"result":20,"param":2,"success":true}
-
{"result":30,"param":3,"success":true}
-
{"result":40,"param":4,"success":true}
-
{"result":50,"param":5,"success":true}
-
{"result":60,"param":6,"success":true}
-
{"result":70,"param":7,"success":true}
-
{"result":80,"param":8,"success":true}
-
{"result":90,"param":9,"success":true}
-
{"result":100,"param":10,"success":true}
-
{"result":110,"param":11,"success":true}
-
{"result":120,"param":12,"success":true}