线程创建的四种方式
创建线程的方式有四种:
- 继承Thread类;
- 实现Runnable接口;
- 实现Callable接口,通过
FutureTask
包装器来创建Thread类; - 通过线程执行器接收实现Runnable、Callable对象,通过Future下面的submit或者execute方法执行;
继承Thread类
package BingFa;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.Executor;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.concurrent.FutureTask;
import java.util.concurrent.ScheduledExecutorService;
/**
* 创建线程的四种方式
*
* @author lsq_adm
*
*/
public class CreateThread {
public static void createThread1(){
// 继承Thread类
Thread t1 = new CreateThreadBy1();
t1.start();
}
}
/* 继承Thread类*/
class CreateThreadBy1 extends Thread {
@Override
public void run() {
System.out.println(this.getName() + " 继承Thread -- 线程1");
}
}
Thread-0 继承Thread -- 线程1
实现Runnable接口
public class CreateThread {
public static void createThread1(){
// 实现Runnable接口
Thread t2 = new Thread(new Runnable(){
@Override
public void run() {
System.out.println(Thread.currentThread().getName() +
"实现 RUnable -- 线程2");
}
});
t2.start();
}
}
Thread-1实现 RUnable -- 线程2
实现Callable接口
通过Callable
+ FutureTask
创建的线程可以有返回值
public class CreateThread {
public static void createThread1(){
// 实现Callable的接口 ,这种方法可从线程中返回值
FutureTask ft = new FutureTask(new Callable(){
@Override
public Object call() throws Exception {
System.out.println(Thread.currentThread().getName()
+ "实现Callable接口 -- 线程3");
return null;
}
});
Thread t3 = new Thread(ft);
t3.start();
}
}
Thread-2实现Callable接口 -- 线程3
通过线程器ExecutorService
类
Executors + ExecutorService + Future
Executors
:提供创建多种线程池的工厂方法;
ExecutorService
:提供执行线程的方法execute(继承自Executor
),返回Future
的submit方法;
Future
:get方法等待任务计算完成,然后检索其结果;
public class CreateThread {
public static void createThread1(){
// 固定线程池
ExecutorService fixedThreadPool = Executors.newFixedThreadPool(5);
// ExecutorService 执行 实现Runable接口的线程 任务
fixedThreadPool.execute(new Runnable(){
@Override
public void run() {
System.out.println(Thread.currentThread().getName()
+ "ExecutorService execute Runnable -- 线程4");
}
});
// ExecutorService 提交 实现Runable接口的线程 任务
Future submit = fixedThreadPool.submit(new Runnable(){
public void run() {
System.out.println(Thread.currentThread().getName()
+ "ExecutorService submit Runnable -- 线程4");
}
});
try {
// Future 的get方法 : 等待计算完成,然后检索其结果
submit.get();
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
// ExecutorService 提交 实现Callable接口的线程 任务
Future<String> submit2 = fixedThreadPool.submit(new Callable(){
@Override
public String call() throws Exception {
return Thread.currentThread().getName()
+ "ExecutorService submit Callable -- 线程5";
}
});
try {
String str = submit2.get();
System.out.println(str);
} catch (InterruptedException e) {
e.printStackTrace();
} catch (ExecutionException e) {
e.printStackTrace();
}
// 可缓存线程池
ExecutorService cachedThreadPool = Executors.newCachedThreadPool();
// 单工作线程
ExecutorService singleThreadExecutor = Executors.newSingleThreadExecutor();
// 支持延迟,定时任务
ScheduledExecutorService scheduledThreadPool =
Executors.newScheduledThreadPool(5);
// 支持延迟,定时任务的单线程
ScheduledExecutorService singleThreadScheduledExecutor =
Executors.newSingleThreadScheduledExecutor();
}
}
pool-1-thread-1ExecutorService execute Runnable -- 线程4
pool-1-thread-2ExecutorService submit Runnable -- 线程5
pool-1-thread-3ExecutorService submit Callable -- 线程6
自定义线程池
自定义线程池,可以用ThreadPoolExecutor
类创建,它有多个构造方法来创建线程池,用该类很容易实现自定义的线程池;
/* 自定义线程池*/
public static void createThreadPool() {
BlockingQueue<Runnable> arrayBlockingQueue =
new ArrayBlockingQueue<Runnable>(5);
/**
* 自定义线程池的参数
* 核心线程数
* 最大线程数
* 超出核心线程的空闲线程最大保持时间
* 时间单位
* 阻塞队列 BlockingQueue
*/
ThreadPoolExecutor pool = new ThreadPoolExecutor(5,10,10,TimeUnit.SECONDS,arrayBlockingQueue);
Runnable t1 = new MyThread();
Runnable t2 = new MyThread();
Runnable t3 = new MyThread();
Runnable t4 = new MyThread();
Runnable t5 = new MyThread();
Runnable t6 = new MyThread();
pool.execute(t1);
pool.execute(t2);
pool.execute(t3);
pool.execute(t4);
pool.execute(t5);
pool.execute(t6);
}
class MyThread implements Runnable {
/* 线程计数器*/
private static int counter = 0;
private final int count = counter++;
public void run() {
System.out.println( count + "任务 " + Thread.currentThread().getName());
}
}
0任务 pool-1-thread-1
2任务 pool-1-thread-3
1任务 pool-1-thread-2
5任务 pool-1-threa-3
4任务 pool-1-thread-5
3任务 pool-1-thread-4