LoadingCache<Key, Graph> graphs = CacheBuilder.newBuilder()
.maximumSize(1000)
.build(
new CacheLoader<Key, Graph>() {
public Graph load(Key key) throws AnyException {
return createExpensiveGraph(key);
}
});
createExpensiveGraph
方法可能需要很长时间才能返回值。我想在load
方法中设置一个时间限制,这样如果createExpensiveGraph
方法在有限的时间内没有返回值,则抛出TimeLimitedException
。如何在load
方法中设置时间限制?
编辑:纠正使用newSingleThreadExecutor
作为pointed out by eclps。
您可以使用Callable
和ExecutorService
来实现超时行为:
final ExecutorService executor = Executors.newSingleThreadExecutor();
final LoadingCache<Key, Graph> graphs = CacheBuilder.newBuilder()
.maximumSize(1000)
.build(
new CacheLoader<Key, Graph>() {
public Graph load(final Key key) throws Exception {
return executor.submit(new Callable<Graph>() {
@Override
public Graph call() {
return createExpensiveGraph(key);
}
}).get(MY_TIME_LIMIT_SECONDS, TimeUnit.SECONDS);
}
});
在get
呼叫网站:
final Graph graph;
try {
graph = graphs.get(myKey);
}
catch (ExecutionException executionException) {
final Throwable cause = Throwables.getRootCause(executionException);
if (cause instanceof TimeoutException) {
// timeout specific logic
}
// other error handling
}
// use graph
由于MoreExecutors.sameThreadExecutor()
,Paul Bellora所写的例子不起作用。
从javadocs为MoreExecutors.sameThreadExecutor()
:
在将Future返回给调用者之前,任务将运行完成(除非执行程序已关闭)。
因此,在get
完成执行之后,才会调用关于Future的createExpensiveGraph
。使用Executors.newSingleThreadExecutor()
或类似的Executor来支持超时。