一.创建多线程的一共有四种方式
方式一:
通过继承Thread,重写run方法,创建实例,执行start方法。
优点:代码编写简单。
缺点:没有返回值,java是单继承,继承一个类后,不能再集成其他类了,扩展性差。
代码如下:
public class ThreadDemo extends Thread {
@Override
public void run() {
System.out.println("继承Thread实现多线程,名称:"+Thread.currentThread().getName());
}
}
public static void main(String[] args) {
ThreadDemo threadDemo1 = new ThreadDemo();
threadDemo.setName("ThreadDemoOne");
threadDemo.start();
System.out.println("主线程名称:"+Thread.currentThread().getName());
}
方式二:
通过实现Runnable。定义的类需实现Runnable,实现里面的run方法,创建Thread实例,使用Runnable接口的实现对象作为参数传递给thread对象,调用Start方法。
优点:线程类可以实现多个接口,可以再继承一个类。
缺点:没有返回值,不能直接启动,需要通过构建Thread的实例传递进去启动。
代码如下:
public class ThreadRunnableDemo implements Runnable {
@Override
public void run() {
System.out.println("通过Runnable实现多线程,名称:"+Thread.currentThread().getName());
}
}
public static void main(String[] args) {
ThreadRunnableDemo threadRunnableDemo = new ThreadRunnableDemo ();
Thread thread = new Thread(threadRunnableDemo);
thread.setName("threadRunnableDemoTwo");
thread.start();
System.out.println("主线程名称:"+Thread.currentThread().getName());
}
方式三:
通过Callable和FutureTask方式。创建Callable接口的实现类,并重写call方法,结合FutureTask类包装Callable对象。
优点:有返回值,扩展性高
缺点:jdk5以后才支持,需要重写call方法,需要结合FutureTask和Thread等类。
代码如下:
public class MyTask implements Callable<Object> {
@Override
public Object call() throws Exception {
System.out.println("通过Callable实现多线程,名称:"+Thread.currentThread().getName());
return "返回值内容";
}
}
public static void main(String[] args) {
MyTask myTask = new MyTask();
FutureTask<Object> futureTask = new FutureTask<>(myTask);
//FutureTask继承了Runnable,可以放在Thread中启动执行
Thread thread = new Thread(futureTask);
thread.setName("demo3");
thread.start();
System.out.println("主线程名称:"+Thread.currentThread().getName());
try {
System.out.println(futureTask.get());
} catch (InterruptedException e) {
//阻塞等待中被中断,则抛出
e.printStackTrace();
} catch (ExecutionException e) {
//执行过程发送异常被抛出
e.printStackTrace();
}
}
方式四:
通过线程池创建线程。自定义类实现Runnable接口,实现run方法,创建线程池,调用执行方法并传入对象。
优点:安全且高性能,复用线程。
缺点:jdk5以后才支持,需要结合Runnable一起使用。
代码如下:
public class ThreadDemo4 implements Runnable {
@Override
public void run() {
System.out.println("通过线程池+runnable实现多线程,名称:"+Thread.currentThread().getName());
}
}
public static void main(String[] args) {
ExecutorService executorService = Executors.newFixedThreadPool(3);
for(int i=0;i<10;i++){
executorService.execute(new ThreadDemo4());
}
System.out.println("主线程名称:"+Thread.currentThread().getName());
//关闭线程池
executorService.shutdown();
}
小结:
- 一般常用的实现Runnable接口的方式 和创建线程池+Runnable,简单方便扩展,和高性能 (池化的思想)。