gpt4 book ai didi

JavaFX 任务可调用

转载 作者:行者123 更新时间:2023-11-30 02:04:13 25 4
gpt4 key购买 nike

我正在开发一个 JavaFX 应用程序,并且在 ExecutorService submit 方法中提供 JavaFX 任务。另外,我试图在 Future 对象中提交的返回值中获取 Task 的返回值。然后我发现 ExecutorService 仅在提交 Callable 对象时返回值,而 JavaFX 任务尽管具有 call 方法,但仍可运行。那么这个问题有什么解决办法吗?

我尝试以这种方式解决了我的问题,但当我不想编写自己的类时,我愿意接受建议。

我的主要方法:

public static void main(String[] args) throws InterruptedException, ExecutionException {
ExecutorService executorService = Executors.newSingleThreadExecutor();
Semaphore semaphore = new Semaphore(1);
List<Integer> list = IntStream.range(0,100).boxed().collect(Collectors.toList());
Iterator<Integer> iterator = list.iterator();
while (iterator.hasNext()){
List<Integer> sendingList = new ArrayList<>();
for (int i = 0; i < 10; i++) {
sendingList.add(iterator.next());
}
System.out.println("SUBMITTING");
Future<Integer> future = executorService.submit((Callable<Integer>) new TestCallable(sendingList,semaphore));
System.out.println(future.get());
semaphore.acquire();
}
executorService.shutdown();
System.out.println("COMPLETED");
}

我的TestCallable类:

class TestCallable extends Task<Integer> implements Callable<Integer> {

private Random random = new Random();
private List<Integer> list;
private Semaphore semaphore;

TestCallable(List<Integer> list, Semaphore semaphore) {
this.list = list;
this.semaphore = semaphore;
}

@Override
public Integer call(){
System.out.println("SENDING");
System.out.println(list);
try {
Thread.sleep(1000+random.nextInt(500));
} catch (InterruptedException e) {
e.printStackTrace();
}
System.out.println("RECEIVED");
semaphore.release();
return list.size();
}
}

最佳答案

Task 扩展了 java.util.concurrent.FutureTask,后者又实现了 Future 接口(interface)。这意味着您可以像使用 Future 一样使用 Task

Executor executor = ...;
Task<?> task = ...;
executor.execute(task);
task.get(); // Future method

这将导致调用 get() 的线程等待直到完成。然而,Task 的目的是与 JavaFX 应用程序线程传达后台进程的进度。它与 GUI 的密切关系意味着您很可能从 FX 线程启动 Task。这将导致在 FX 线程上调用 get(),这不是您想要的,因为它将卡住 GUI,直到 get() 返回;您不妨直接调用 Task.run

相反,您应该使用 Task 提供的异步功能。如果您想在Task成功完成时检索该值,您可以使用onSucceeded属性或监听value/state 属性。还有一些方法可以监听失败/取消。

Executor executor = ...;
Task<?> task = ...;
task.setOnSucceeded(event -> handleResult(task.getValue()));
task.setOnFailed(event -> handleException(task.getException()));
executor.execute(task);

如果您不需要 Task 提供的功能,那么最好直接使用 RunnableCallable

关于JavaFX 任务可调用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51830500/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com