线程的创建方式
目前创建线程的方式主要有以下三种:
- 继承 java.lang.Thread
- 实现接口 java.lang.Runnable
- 实现接口java.lang.Callable<?>
方式一:继承 java.lang.Thread
Thread类本质上是实现了Runnable接口的一个实例,代表一个线程的实例。启动线程的唯一方法就是通过Thread类的start()实例方法。start()方法是一个native方法,它将启动一个新线程,并执行run()方法。
package com.java.thread; // 线程类 public class CreateByExtsThread extends Thread { @Override public void run() { System.out.println("线程已启动,开始运行"); try { this.sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("线程执行完毕"); } }
// 测试类 class Ctest01 { public static void main(String[] args) { Thread createByExtsThread = new CreateByExtsThread(); createThreadByExtsThread.start(); } }
方式二:实现接口 java.lang.Runnable
如果自己的类已经extends另一个类,就无法直接extends Thread,此时,可以实现一个Runnable接口。
package com.java.thread; // 线程类 public class CreateByImplRunnable implements Runnable { @Override public void run() { System.out.println("线程已启动,开始运行"); try { Thread.currentThread().sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("线程执行完毕"); } }
// 测试类 class Ctest02 { public static void main(String[] args) { Runnable runnable = new CreateByImplRunnable(); Thread thread = new Thread(runnable); thread.start(); } }
方式三:实现接口java.lang.Callable<?>
package com.java.thread; import java.util.concurrent.Callable; import java.util.concurrent.ExecutionException; import java.util.concurrent.FutureTask; // 线程类 public class CreateByImplCallable implements Callable<String> { @Override public String call() throws Exception { System.out.println("线程已启动,开始运行"); try { Thread.currentThread().sleep(1000); } catch (InterruptedException e) { e.printStackTrace(); } System.out.println("线程执行完毕"); // 线程执行完后返回当前线程的名称 return Thread.currentThread().getName(); } }
// 测试类 class Ctest03 { public static void main(String[] args) { Callable<String> callable = new CreateByImplCallable(); FutureTask<String> futureTask = new FutureTask<>(callable); Thread thread = new Thread(futureTask, "thread-createByImplCallable"); thread.start(); try { System.out.println("线程执行完返回的结果:"+futureTask.get()); } catch (InterruptedException e) { e.printStackTrace(); } catch (ExecutionException e) { e.printStackTrace(); } } }
与实现 java.lang.Runnable接口的线程类相比,该种方式能够异步返回线程执行任务的结果。