1.直接看代码中的demo:
package com.landon.mavs.example.concurrent;

import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.concurrent.TimeUnit;

import com.google.common.util.concurrent.FutureCallback;
import com.google.common.util.concurrent.Futures;
import com.google.common.util.concurrent.ListenableFuture;
import com.google.common.util.concurrent.ListeningExecutorService;
import com.google.common.util.concurrent.MoreExecutors;


/** *//**
*
* 使用guava实现异步回调 {@link java.util.concurrent.Future}
* {@link com.google.common.util.concurrent.ListenableFuture}
* {@link com.google.common.util.concurrent.FutureCallback}
*
* @author landon
*
*/

public class FutureCallbackExample
{

public static void main(String[] args) throws Exception
{
// 原生的Future模式,实现异步
ExecutorService nativeExecutor = Executors.newSingleThreadExecutor();
Future<String> nativeFuture = nativeExecutor

.submit(new Callable<String>()
{

@Override

public String call() throws Exception
{
// 使用sleep模拟调用耗时
TimeUnit.SECONDS.sleep(1);
return "This is native future call.not support async callback";
}
});

// Future只实现了异步,而没有实现回调.所以此时主线程get结果时阻塞.或者可以轮训以便获取异步调用是否完成
System.out.println(nativeFuture.get());

// 好的实现应该是提供回调,即异步调用完成后,可以直接回调.本例采用guava提供的异步回调接口,方便很多.
ListeningExecutorService guavaExecutor = MoreExecutors
.listeningDecorator(Executors.newSingleThreadExecutor());
final ListenableFuture<String> listenableFuture = guavaExecutor

.submit(new Callable<String>()
{

@Override

public String call() throws Exception
{
Thread.sleep(1000);
return "this is guava future call.support async callback";
}
});

// 注册监听器,即异步调用完成时会在指定的线程池中执行注册的监听器

listenableFuture.addListener(new Runnable()
{

@Override

public void run()
{

try
{
System.out.println("async complete.result:"
+ listenableFuture.get());

} catch (Exception e)
{
}
}
}, Executors.newSingleThreadExecutor());

// 主线程可以继续执行,异步完成后会执行注册的监听器任务.
System.out.println("go on execute.asyn complete will callback");

// 除了ListenableFuture,guava还提供了FutureCallback接口,相对来说更加方便一些.
ListeningExecutorService guavaExecutor2 = MoreExecutors
.listeningDecorator(Executors.newSingleThreadExecutor());
final ListenableFuture<String> listenableFuture2 = guavaExecutor2

.submit(new Callable<String>()
{

@Override

public String call() throws Exception
{
Thread.sleep(1000);
System.out.println("asyncThreadName:"
+ Thread.currentThread().getName());
return "this is guava future call.support async callback using FutureCallback";
}
});
// 注意这里没用指定执行回调的线程池,从输出可以看出,默认是和执行异步操作的线程是同一个.

Futures.addCallback(listenableFuture2, new FutureCallback<String>()
{

@Override

public void onSuccess(String result)
{
System.out
.println("async callback(using FutureCallback) result:"
+ result);
System.out.println("execute callback threadName:"
+ Thre }ad.currentThread().getName());


@Override

public void onFailure(Throwable t)
{
}
});
}
}

2.总结:利用guava的ListenableFuture和FutureCallback方便的实现异步回调.
posted on 2014-02-27 14:54
landon 阅读(7185)
评论(3) 编辑 收藏 所属分类:
Program