一般来说,创建线程有三种方式:继承 Thread 类、实现 Runnable 接口和实现 Callable 接口。
继承 Thread 类:继承 Thread 类,重写 run() 方法,调用 start() 方法启动线程。
public class MyThread {public static class MyThreadTest1 extends Thread {@Overridepublic void run() {System.out.println("继承 Thread 类");}}public static void main(String[] args) {MyThreadTest1 myThreadTest1 = new MyThreadTest1();myThreadTest1.start();}}
实现 Runnable 接口:实现 Runable 接口,重写 run() 方法。
public class Mythread2 implements Runnable {@Overridepublic void run() {System.out.println("实现 Runnable 接口");}public static void main(String[] args) {Mythread2 mythread2 = new Mythread2();new Thread(mythread2).start();}}
可以看到以上两种方式都是在调用 start() 方法时调用了 run() 方法,那为什么不能直接去调用 run() 方法呢?其实以上这两种方式如果直接调用 run() 方法的时候也是能成功执行的。
JVM 在执行 start() 方法时,会先创建一个新线程,由创建出来的新线程去执行 Thread 的 run() 方法,这才起到多线程的效果。如果直接调用 Thread 的 run() 方法,那么 run() 方法还是运行在主线程中,相当于顺序执行,就起不到多线程的效果。
以上这两种创建线程的方法都是没有返回值的,如果我们需要关注线程执行结果的话,就需要第三种创建线程的方式。
实现 Callable 接口:实现 Callable 接口,重写 call() 方法,这种方式可以通过 FutureTask 获取任务执行的返回值。
public class MyThread3 implements Callable {@Overridepublic Object call() throws Exception {return "实现 Callable 接口";}public static void main(String[] args) {//创建异步任务FutureTask<String> task=new FutureTask<String>(new MyThread3());//启动线程new Thread(task).start();try {//等待执行完成,并获取返回结果String result = task.get();System.out.println(result);} catch (Exception e) {e.printStackTrace();}}
}
本文参考自:面渣逆袭:Java并发六十问,快来看看你会多少道! - 掘金