Android十八章:Java线程中的Runnable,Callable,Future,FutureTask

前言,在java线程中最常见的是Thread 和Runnable,很少见到或者用到callable等类。但是,你接触过android源码就会经常看到这些类,比如AsyncTask的源码在execute方法源码可以看到了这些类。在面试时也有可能会问到两者的区别,所以现在容许鄙人来介绍一下java中这些类的用法。

Runnable

Runnable一个接口类,包括一个run的接口方法:通常我们会自定义一个类去实现Runnable,这时候还可以实现其他接口方法,如果类要是继承Thread就不能再继承其他类了。

public interface Runnable{
  public abstract void run();
}

Runnable 通常配合Thread使用,在run方法里面写耗时的操作:

new Thread(new Runnable(){
  public void run(){
  // 
 }
}).start();

Callable

Callable是一个泛型接口,要比Runnable强些 ,因为接口方法call有返回值,并且返回值是传入的泛型类型,还能call的过程中抛出异常。

public interface Callable{
  V call() throws Exception;
}

示例要配合Future或者FutureTask来执行。

Future

Future是一个泛型接口类,是Runnable和Callable的调度容器,就是对Runnable和Callable的结果进行操作,比如:

  1. isCancelled()取消操作,call方法任务完成前取消,返回true。
  2. isDone()判断是否操作完成,是则返回true。
  3. get()获取操作结果,会导致程序阻塞,必须等到子线程结束才会得到返回值。
  4. get(long timeout TimeUnit unit)在某时间后获取操作结果,如果在规定时间内获取不到返回值将会抛出超时异常)
public interface Future{
  boolean isCancelled();
  boolean isDone();
  V get() throws InterputeredException,ExecutionExeception;
  V get(long timeout ,TimeUnit unit)throws InterputeredException,ExecutionExeception,TimeoutExeception;
  
}

比如

ExecutorService threadPool=Executors.newSingleThreadExecutor();
Future future=threadPool.submit(new Callable(){
  public String call()throws Exception{
    return "result";
  }
  
});

Futurn.get();//返回操作结果

FutureTask

FutureTask类同时实现了Runnable和Future 两个接口,具有了两个接口的属性。

public class FutureTask implements RunnableFuture{
  public FutureTask(Callable callable){
       this.callable=callable;
       ...
     }
  public FutureTask(Runnable runnable,V result){
    this.callable=Executors.callable(runnable,result);
    ...
  }
  boolean isCancelled();
  boolean isDone();
  V get() throws InterputeredException,ExecutionExeception;
  V get(long timeout ,TimeUnit unit)throws InterputeredException,ExecutionExeception,TimeoutExeception;
}
public interface RunnableFuture implements Runnable,Future{
  void run();
}

这里的FutureTask间接实现了两个接口,在FutureTask的构造方法传入Callable或者是Runnable,而Runnable会转为Callable,runnable通过runnableadapter转为callable。同时FutureTask还具备Future的所有方法。

举个例子

Callable callable=new Callable(){
  public Ingeter call() throws Exception{
    return 100;
  }
};
FutureTask task=new FutureTask(callable);
new Thread(task).start();

task.get();//当然要先启动线程才能得到结果;

这里的callable当成runnable用了。

总结

  1. Callable比Runnable高级能返回结果值和抛出异常

  2. 可以有上述例子看到Callable来产生结果,Futuretask来获取结果。

  3. 在获取结果期间还可以控制是否取消thread 判断thread是否完成。

  4. FutureTask调用get方法获取call返回值过程中,主线程会阻塞,直到call方法结束并且返回。

你可能感兴趣的:(Android十八章:Java线程中的Runnable,Callable,Future,FutureTask)