【发布时间】:2021-12-05 17:10:20
【问题描述】:
我正在使用 Java(非 Android)开发一个项目。我有一个做一些长时间工作的线程,我希望在工作完成后调用主线程中的一个函数。我已经看到很多关于这个问题的问题,但似乎没有任何答案有效。我当前的实现如下所示:
- 有一个带有回调函数的接口
- 将该接口作为runnable中的参数
- 在主类中实现,然后创建runnable并启动一个新线程。
- 在回调函数中,打印当前线程名称
这不起作用,因为当线程完成时,它总是打印新线程的名称,而不是主线程的名称。如何使回调函数在主线程上调用,而不在新线程上调用?
谢谢!
编辑:这是我尝试过的代码:
import java.util.Random;
public class ATestThreadClass {
public static void main(String[] args) {
new Thread(new RandomRunnable(data -> {
System.out.println("Called on " + Thread.currentThread().getName());
System.out.println(data.toString());
})).start();
}
static class RandomRunnable implements Runnable {
private final CallbackInterface callbackInterface;
public RandomRunnable(CallbackInterface callbackInterface) {
this.callbackInterface = callbackInterface;
}
@Override
public void run() {
// Do some very long work...
Random random = new Random();
RandomCallbackData data = new RandomCallbackData();
data.a = random.nextInt(100);
data.b = random.getClass().getSimpleName();
data.c = random.nextLong();
callbackInterface.callback(data); // THIS REALLY NEEDS TO BE CALLED ON THE MAIN THREAD
}
}
interface CallbackInterface {
void callback(RandomCallbackData data);
}
static class RandomCallbackData {
public int a;
public String b;
public long c;
@Override
public String toString() {
return "RandomCallbackData{" +
"a=" + a +
", b='" + b + '\'' +
", c=" + c +
'}';
}
}
}
(对不起,奇怪的格式;当我粘贴代码时堆栈溢出搞砸了)
以下是日志:
Called on Thread-3
RandomCallbackData{a=77, b='Random', c=-7871432476136355770}
Process finished with exit code 0
【问题讨论】:
-
当你说“不工作”时,你能发布你失败的代码吗?多线程错误尤其取决于细节,因此我们需要代码来回答您的问题。
-
在这一位:
How can I make the callback function be called on the main thread你不能,至少没有阻塞或类似的东西(忙着等待)。当前正在执行代码的线程(您的主线程)不会突然跳到其他代码并在那里开始执行。任何系统上的线程模型都不是这样工作的。这听起来像是一个 X-Y 问题,您可能想告诉使用您实际想要完成的任务。 -
“正确”的做法是记录行为。让编写回调函数的人清楚,它将在与请求回调的线程不同的线程中调用。让他们明确他们有责任使用适当的同步和信号将任何信息传回他们的“主”(或任何其他)线程。
-
我对我的问题进行了编辑
标签: java multithreading callback asynccallback