简介
我们在处理多线程任务时希望在任务被取消或者正常完成后做一些后期处理,例如释放系统资源,更新数据库状态等等。java多线程技术中为我们提供了这样一个类叫FutureTask,他可以帮助我们实现任务在done状态后可以做一些后期处理。
例子
import java.util.concurrent.Callable;
import java.util.concurrent.TimeUnit;
/**
* 实现Callable接口,是一个可以获取返回值的任务
* @author liujun
*/
public class ExecutableTask implements Callable<String> {
private String name;
public ExecutableTask(String name) {
this.name = name;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
@Override
public String call() throws Exception {
long duration = (long)(Math.random()*10);
System.out.println("name:"+this.name+"-duration:"+duration);
TimeUnit.SECONDS.sleep(duration);
return "hello world,I'm "+name;
}
}
import java.util.concurrent.Callable;
import java.util.concurrent.FutureTask;
/**
* 自定义FutureTask,重写done方法
* 可以在任务处于done状态时关闭资源、输出日志信息、发送通知等
* 但是无法改变任务的结果值
* @author liujun
*/
public class ResultTask extends FutureTask<String> {
private String name;
/**真正的任务*/
private ExecutableTask task;
public ResultTask(Callable<String> callable) {
super(callable);
this.task = (ExecutableTask) callable;
this.name = this.task.getName();
}
//whether normally or via cancellation
//在任务正常结束或者被取消时回调
@Override
protected void done() {
if (this.isCancelled()) {//任务被取消
System.out.println(this.name+" has bean cancel");
}else{//任务正常结束
System.out.println(this.name+" has bean finished");
}
}
}
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;
public class Main {
public static void main(String[] args) {
//线程池
ExecutorService executor = Executors.newCachedThreadPool();
//是一个Runnable
ResultTask[] resultTasks = new ResultTask[5];
//执行5个任务
for (int i = 0; i < 5; i++) {
ExecutableTask task = new ExecutableTask("Task "+i);
resultTasks[i] = new ResultTask(task);
executor.submit(resultTasks[i]);
}
//暂停5秒钟后取消所有任务
try {
TimeUnit.SECONDS.sleep(3);
} catch (InterruptedException e) {
e.printStackTrace();
}
for (int i = 0; i < 5; i++) {
resultTasks[i].cancel(true);
}
//查询任务是否被取消
for (int i = 0; i < 5; i++) {
if (!resultTasks[i].isCancelled()) {
try {
System.out.println(""+resultTasks[i].get());
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
}
}
//关闭线程池
executor.shutdown();
}
}
结果
name:Task 0-duration:1name:Task 1-duration:8
name:Task 2-duration:7
name:Task 3-duration:9
name:Task 4-duration:6
Task 0 has bean finished
Task 1 has bean cancel
Task 2 has bean cancel
Task 3 has bean cancel
Task 4 has bean cancel
hello world,I'm Task 0