创建和使用匿名Runnable类的最佳方法

hqt*_*hqt 36 java multithreading runnable

我想为runnable使用匿名类.有两种方法,但我不知道他们是否做同样的事情:

方法一:直接使用Runnable和call run

new Runnable() {
    @Override
    public void run() {
    }
}.run();
Run Code Online (Sandbox Code Playgroud)

方法二:创建一个匿名的runnable,并使用start方法而不是run来粘贴到Thread:

new Thread(new Runnable() {
    @Override
    public void run() {
    }
}).start();
Run Code Online (Sandbox Code Playgroud)

我认为方法二显然是正确的.但是,我不知道它是否与方法一相同?我们可以Runnable直接在Runnable上调用方法吗?

谢谢 :)

Hov*_*els 26

不,你通常不会run()直接在Runnable上调用,因为你没有这样的背景线程.如果你不想要并且需要后台线程,那么run()直接进行精细调用,否则如果你想创建一个后台线程并从中运行你的Runnable,你必须创建一个新的Thread然后将Runnable传入它的构造函数,并打电话start().

此外,还有其他方法可以完成此任务,包括使用Executor和ExecutorServices,您应该研究它的用途,因为它们比使用裸骨线程对象提供更多的灵活性和功能.

此外,您还需要查看Future接口和FutureTasks类的使用,它们类似于Runnables,它们允许您在完成时返回结果.如果您使用过SwingWorker,那么您已经使用了Future接口而没有意识到它.


jak*_*son 26

正如其他人所提到的,使用Thread类是正确的方法.但是,您还应该考虑使用Javas Executors框架来处理正在运行的线程.

Executors.newSingleThreadExecutor().execute(new Runnable() {
    @Override 
    public void run() {
        // code in here
    }
});
Run Code Online (Sandbox Code Playgroud)

当然,直接使用Thread很好.但通常建议(或首选)使用该框架.让Java为您处理精细的细节.


yla*_*idi 6

你的方法1不会产生感觉.Runnable只有在Thread(您的方法2)中执行时,该接口才对线程有意义.如果你想找到另一种内联方式,一个Thread内的一大块代码,这可能是一个:

Thread t = new Thread()
{
     public void run()
     {
        // put whatever code you want to run inside the thread here.
     }
};
t.start();
Run Code Online (Sandbox Code Playgroud)


fm-*_*sys 6

Runnable 的初始化可以通过 lambda 表达式完成:

Runnable myRunnable = () -> {
    //code you want to execute
};
Run Code Online (Sandbox Code Playgroud)

直接调用myRunnable.run()将在同一线程上执行代码。如果它应该异步运行,您需要通过调用new Thread(myRunnable).start()或内联 lambda 将其包装在线程内:

new Thread(() -> {
    //code you want to execute
}).start();
Run Code Online (Sandbox Code Playgroud)