在Javaservlet中将Runnable.run()转换为Callable.call()
在下面的代码中,我无法将带有可运行接口的代码转换为可调用接口。我需要更改,因为我需要通过线程返回在Javaservlet中将Runnable.run()转换为Callable.call(),java,servlets,runnable,callable,Java,Servlets,Runnable,Callable,在下面的代码中,我无法将带有可运行接口的代码转换为可调用接口。我需要更改,因为我需要通过线程返回Sting[][]isRs 当我将接口更改为callable和chande.run()为.call(),然后新建线程(新工作线程(startSignal,doneSignal,I)).start()不起作用 CountDownLatch startSignal = new CountDownLatch(1); CountDownLatch doneSignal = new CountDownLatch
Sting[][]isR
s
当我将接口更改为callable
和chande.run()
为.call()
,然后新建线程(新工作线程(startSignal,doneSignal,I)).start()代码>不起作用
CountDownLatch startSignal = new CountDownLatch(1);
CountDownLatch doneSignal = new CountDownLatch(3); // 3 tasks
class Worker implements Runnable {
private final CountDownLatch startSignal;
private final CountDownLatch doneSignal;
private final int threadNumber;
// you can pass additional arguments as well
Worker(CountDownLatch startSignal, CountDownLatch doneSignal, int threadNumber) {
this.startSignal = startSignal;
this.doneSignal = doneSignal;
this.threadNumber = threadNumber;
}
public void run() {
try {
startSignal.await();
if (threadNumber == 1) {
String[][] isRs = getIS(erg1, erg2, request);
}
if (threadNumber == 2) {
getIW(erg1, erg2, request);
}
if (threadNumber == 3) {
getIN(search_plz, request);
}
doneSignal.countDown();
} catch (InterruptedException ex) {
System.out.println(ex);
}
}
}
// 3 new threads are started
for (int i = 1; i <= 3; i++) {
new Thread(new Worker(startSignal, doneSignal, i)).start();
}
startSignal.countDown(); // let all threads proceed
try {
doneSignal.await(); // wait for all to finish
// all 3 tasks are finished and do whatever you want to do next
} catch (Exception e) {
}
CountDownLatch startSignal=新的CountDownLatch(1);
CountDownLatch doneSignal=新的CountDownLatch(3);//3项任务
类工作者实现可运行的{
私人最终倒计时闩锁启动信号;
私人最终倒计时信号;
私有最终整数线程数;
//您还可以传递其他参数
辅助程序(CountDownLatch startSignal、CountDownLatch doneSignal、int threadNumber){
this.startSignal=startSignal;
this.doneSignal=doneSignal;
this.threadNumber=threadNumber;
}
公开募捐{
试一试{
开始信号。等待();
if(threadNumber==1){
字符串[][]isRs=getIS(erg1、erg2、request);
}
if(threadNumber==2){
getIW(erg1,erg2,请求);
}
if(threadNumber==3){
getIN(搜索、请求);
}
doneSignal.countDown();
}捕获(中断异常例外){
系统输出打印项次(ex);
}
}
}
//启动3个新线程
对于(int i=1;i您不能将可调用的
传递到线程
中执行
使用ExecutorService
执行Callable
对象
您可以使用它的submit()
方法为它提供可调用的对象:
未来提交(可调用任务)
您的类应该如下所示:
class Worker {
private final CountDownLatch startSignal;
private final CountDownLatch doneSignal;
private final int threadNumber;
Worker(
CountDownLatch startSignal,
CountDownLatch doneSignal,
int threadNumber
){
this.startSignal = startSignal;
this.doneSignal = doneSignal;
this.threadNumber = threadNumber;
}
public String[][] getSomeStrArrArr() {
try {
startSignal.await();
if (threadNumber == 1) {
System.out.println("Running thread number 1");
}
if (threadNumber == 2) {
System.out.println("Running thread number 2");
}
if (threadNumber == 3) {
System.out.println("Running thread number 3");
}
doneSignal.countDown();
} catch (InterruptedException ex) {
System.out.println(
"Thread number "+threadNumber+" has been interrupted."
);
}
// replace these 2 lines with the actual code to get the String[][]
String[][] someStrArrArr = new String[1][1];
someStrArrArr[0][0] = "Done with thread number "+threadNumber;
return someStrArrArr;
}
public Callable<String[][]> getSomeCallableStrArrArr(){
return new Callable<String[][]>() {
public String[][] call() throws Exception {
return getSomeStrArrArr();
}
};
}
}
类工作者{
私人最终倒计时闩锁启动信号;
私人最终倒计时信号;
私有最终整数线程数;
工人(
倒计时闩锁启动信号,
倒计时信号,
整数线程数
){
this.startSignal=startSignal;
this.doneSignal=doneSignal;
this.threadNumber=threadNumber;
}
公共字符串[][]GetSomeStrarrr(){
试一试{
开始信号。等待();
if(threadNumber==1){
System.out.println(“运行线程编号1”);
}
if(threadNumber==2){
System.out.println(“运行线程编号2”);
}
if(threadNumber==3){
System.out.println(“运行线程编号3”);
}
doneSignal.countDown();
}捕获(中断异常例外){
System.out.println(
“螺纹编号”+螺纹编号+“已中断。”
);
}
//用实际代码替换这两行以获取字符串[][]
字符串[][]somestrarrar=新字符串[1][1];
someStrArrArr[0][0]=“使用线程编号完成”+线程编号;
返回somestrarrar;
}
公共可调用getSomeCallableStrarrr(){
返回新的可调用(){
公共字符串[][]调用()引发异常{
返回getSomeStrarrr();
}
};
}
}
你可以这样开始:
ExecutorService pool = Executors.newFixedThreadPool(3);
Set<Future<String[][]>> set = new HashSet<Future<String[][]>>();
CountDownLatch startSignal = new CountDownLatch(1);
CountDownLatch doneSignal = new CountDownLatch(3);
for (int i=1;i<=3;i++) {
Worker worker = new Worker(startSignal,doneSignal,i);
Callable<String[][]> callable =
worker.getSomeCallableStrArrArr();
Future<String[][]> future = pool.submit(callable);
set.add(future);
}
ExecutorService池=Executors.newFixedThreadPool(3);
Set=newhashset();
CountDownLatch startSignal=新的CountDownLatch(1);
CountDownLatch doneSignal=新的CountDownLatch(3);
对于(inti=1;i一旦您的类实现了可调用接口,您将拥有方法调用及其返回类型
您可以将以下代码用于ExecutorService:-
ExecutorService service = Executors.newSingleThreadExecutor();
Worker worker= new Worker (tartSignal, doneSignal,threadNumber);
Future<Integer> future = service.submit(worker);
Object result = future.get();
ExecutorService service=Executors.newSingleThreadExecutor();
Worker-Worker=新的Worker(tartSignal、doneSignal、threadNumber);
未来=服务。提交(工人);
对象结果=future.get();
希望这将有助于解决您的问题。不要使用原始线程,请使用ExecutorService
。或者,更好的是,使用Java 8CompletableFuture
。如何做到这一点,这是否解决了我的问题?从那里开始并从那里开始工作。我要注意,如果threadNumber==x
,您的可以通过多态性解决,resulting在更干净的代码中。为什么要将可运行
更改为可调用
?此代码非常错误。您的工作者
未编译。“应该看起来像”与“应该是”不同。如果你想学习一些东西,你必须付出一些努力。为了更清楚,我编辑并替换了代码片段中一些模棱两可的部分。目的是让OP了解所需更改的主要内容,以便使用可调用接口而不是可运行接口;为他指明正确的方向,而不是为h编写代码尽管如此,欢迎你提供一个更好的例子。谢谢你的回答,但是如果我正确理解你的例子,它对我没有帮助。我使用不同线程的原因是,所有3个任务都应该同时处理,因为它们需要一些时间。在你的例子中,它们将被同步处理,因为它们等待返回还是我错了?@BoristheSpider根据我的理解,elcodedocle提供的代码可以很好地解释如何实现逻辑。最终目标是解释用户,以便他能够获得帮助来解决小的编译问题。好的,你完全正确。它是并行的。所以现在我已经设置了3个线程的3个结果?我如何获得t3字符串[][]结果超出设置范围?谢谢。Object result是call()的返回值吗?如何从结果中获取返回的字符串[][]。另一个问题是,我的start和stopSignal不再工作了。好的,start和stopSignal正在工作,但如何获得返回值?在实现可调用的inter之后,在worker类中
ExecutorService service = Executors.newSingleThreadExecutor();
Worker worker= new Worker (tartSignal, doneSignal,threadNumber);
Future<Integer> future = service.submit(worker);
Object result = future.get();