2011-04-27 92 views
1

我想在x秒后停止该方法。 我该怎么做?在java中为方法创建超时的最佳方式是什么?

编辑
我会详细说明: 我的方法()是本地的或与其他服务器通信。
我不在一个循环(因此我不能改变一个标志) 我会想要使用方法的返回值,如果它存在。

+5

请参阅http://stackoverflow.com/questions/2733356/killing-thread-after-some-specified-time-limit-in-java – armandino 2011-04-27 06:35:59

回答

2

,在很大程度上取决于你的方法做。最简单的方法是定期检查方法执行的时间,并在超出限制时返回。

long t0 = System.currentTimeMillis(); 
// do something 
long t1 = System.currentTimeMillis(); 
if (t1-t0 > x*1000) { 
    return; 
} 

如果你想运行在一个单独的线程的方法,那么你可以做这样的事情:

public <T> T myMethod() { 
    ExecutorService executor = Executors.newSingleThreadExecutor(); 
    try { 
     try { 
      T value = executor.invokeAny(Collections.singleton(new Callable<T>() { 
       @Override 
       public T call() throws Exception { 
        //your actual method code here 
        return null; 
       } 
      }), 3, TimeUnit.SECONDS); 
      System.out.println("All went fine"); 
      return value; 
     } catch (TimeoutException e) { 
      System.out.println("Exceeded time limit, interrupted"); 
     } catch (Exception e) { 
      System.out.println("Some error happened, handle it properly"); 
     } 
     return null; /*some default value*/ 
    } finally { 
     executor.shutdownNow(); 
    } 
} 

请注意,如果你在线程中做一些未中断IO ,此方法将无法工作。

+0

我可以使用mt方法返回值?像Callable ? – Jeb 2011-04-27 07:07:14

+0

@ user450602是,invokeAny方法返回返回值(请参阅http://download.oracle.com/javase/1.5.0/docs/api/java/util/concurrent/ExecutorService.html)。 – dacwe 2011-04-27 07:18:06

+0

@ user450602请检查更新后的答案 – 2011-04-27 07:25:56

0

这取决于你在做什么以及你需要的准确度。 如果你在循环中,你可以跟踪使用System.currentTimeMillis()已经过了多少时间。只要开始时间,并定期检查并了解已过多久。

你可以产生一个新的线程来开始你的处理,睡眠x秒,然后做一些事情来停止处理线程。

+0

循环将无法正常工作,假设您是使用网络连接,甚至单线可能需要开销时间 – 2011-04-27 07:00:10

1

最可靠的方法 - 就我看来 - 是一个多线程解决方案。我会将长时间运行的算法放在Runnable中,并使用ExecutorService来执行给定超时的线程。

回答this question提供了解决方案的更多细节。

当然,现在的方法将在平行exectued主线程,但你可以强制单个线程的行为Thread#join - 只需用你的主线程等到有时间限制的工作线程完成或超过它的超时限制。

0

你不能这样做,在一次执行必须使用螺纹为

我同意armandino

see this

相关问题