我有一个java应用程序,它必须作为Linux进程运行。它通过套接字连接到远程系统。我有两个线程,贯穿整个程序的生命周期。这是我的应用程序入口点的简短版本:
public class SMPTerminal {
private static java.util.concurrent.ExcecutorService executor;
public static void main(String[] args) {
executor = Executors.newFixedThreadPool(2);
Runtime.getRuntime().addShutdownHook(new Thread(new ShutdownHook()));
run(new SMPConsumer());
run(new SMPMaintainer());
}
public static void run(Service callableService) {
try {
Future<Callable> future = executor.submit(callableService);
run(future.get().restart());
} catch (InterruptedException | ExcecutionException e) {
// Program will shutdown
}
}
}这是Service接口:
public interface Service() {
public Service restart();
}这是Service接口的一个实现:
public class SMPConsumer implements Callable<Service>, Service {
@Override
public Service call() throws Exception {
// ...
try {
while(true) {
// Perform the service
}
} catch (InterruptedException | IOException e) {
// ...
}
return this; // Returns this instance to run again
}
public Service restart() {
// Perform the initialization
return this;
}
}当暂时的IO故障或其他问题导致我的应用程序关闭时,我达到了这个结构。现在,如果我的程序遇到问题,它不会完全关闭,而是从头开始初始化并继续运行。但我认为这有点荒唐,我违反了OOP的设计规则。我的问题
发布于 2014-10-13 07:48:26
您可能没有注意到,但是run方法在callableService返回之前等待它完成执行。因此,您不能同时启动两个服务。这是因为 waits until the task computation completes。
public static void run(Service callableService) {
try {
Future<Callable> future = executor.submit(callableService);
run(future.get().restart()); // <=== will block until task completes!
} catch (InterruptedException | ExcecutionException e) {
// Program will shutdown
}
}(您应该注意到,由于必须捕获InterruptionException --它表明存在一些阻塞、长时间运行的操作)。
这也使执行服务变得无用。如果向执行器提交任务的代码总是等待任务完成,则不需要通过executor执行此任务。相反,提交代码应该直接调用服务。
所以我假设在这种情况下阻塞不是整数的。也许您的run方法应该如下所示:
public static void run(Service callableService) {
executor.submit(() -> {
Service result = callableService.call();
run(result.restart());
return result;
});
}此代码段只是基本代码段,您可能希望将其扩展到处理异常情况。
发布于 2014-10-12 11:30:58
https://stackoverflow.com/questions/26324407
复制相似问题