- 什么是thread
A thread
线程的重要属性:
属性 | 说明 |
priority | 优先级,1-10,一个高优先级的线程比低优先级的线程更偏向于先执行 |
daemon | 守护线程,守护线程是指父线程的守护线程,当父线程停止时守护线程会自动停止,而如果是一个非守护线程,不受影响 |
name | 线程名称,不指定线程名称时, 会自动生成一个带序号递增的线程名称如:Thread-0 Thread-1 |
group | 线程组,不指定线程组时, 默认取父线程的线程组,其父线程为创建该线程的当前线程 |
- 创建线程的2种方式
- 声明一个
Thread
的子类,重写run方法
class PrimeThread extends Thread {
long minPrime;
PrimeThread(long minPrime) {
this.minPrime = minPrime;
}
public void run() {
// compute primes larger than minPrime
}
}
// 创建一个线程并启动
PrimeThread p = new PrimeThread(143);
p.start();
- 声明一个实现
Runnable
接口的类
class PrimeRun implements Runnable {
long minPrime;
PrimeRun(long minPrime) {
this.minPrime = minPrime;
}
public void run() {
// compute primes larger than minPrime
}
}
// 创建一个线程并启动
PrimeRun p = new PrimeRun(143);
new Thread(p).start();
- 线程的生命周期
-
Thread
类的API详解
实例方法
启动线程:t.start()
休眠线程:t.sleep()
中断线程:t.interrupt()
线程是否已被中断:t.isInterrupted()
获取线程未处理异常:t.getDefaultUncaughtExceptionHandler()
等待线程死亡:t.join()
静态方法
释放当前线程的cpu执行权:Thread.yield()
获取当前线程:Thread.currentThread()
线程是否可中断:Thread.interrupted()
线程是否存活:Thread.isAlive()
代码示例:
1、如何确保一个线程终止:假设一个网络连接线程进行网络连接,当连接成功后启动一个心跳检测线程每隔2s发送心跳检测。将心跳检测设置为守护线程setDaemon(true)
,则当网络连接线程关闭后,能保证心跳检测线程随之关闭。
public static void main(String[] args) {
Thread t = new Thread() {
@Override
public void run() {
System.out.println("启动网络连接线程");
Thread innerThread = new Thread() {
@Override
public void run() {
while (true) {
System.out.println("心跳检测");
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
};
innerThread.setDaemon(true);
innerThread.start();
}
};
t.start();
System.out.println("main 线程结束");
}
2、如何优雅的结束一个线程
正常结束
private static class Worker extends Thread {
private volatile boolean start = true;
@Override
public void run() {
while (start) {
//
}
}
public void shutdown() {
this.start = false;
}
}
public static void main(String[] args) throws InterruptedException {
Worker worker = new Worker();
worker.start();
TimeUnit.SECONDS.sleep(1);
worker.shutdown();
}
private static class Worker extends Thread {
@Override
public void run() {
while (true) {
try {
TimeUnit.MICROSECONDS.sleep(1);
} catch (InterruptedException e) {
break;
}
}
/*
while (true) {
if (Thread.interrupted()) {
break;
}
}*/
System.out.println("thread has complete");
}
}
public static void main(String[] args) throws InterruptedException {
Worker worker = new Worker();
worker.start();
TimeUnit.SECONDS.sleep(1);
worker.interrupt();
}
暴力结束
当某个线程访问某个耗时资源,程序又没办法正常中断,可以采用该设计方式
private static class ThreadService {
private Thread executeThread;
private boolean finished;
/**
* 封装执行任务
* @param task
*/
public void execute(Runnable task) {
executeThread = new Thread() {
@Override
public void run() {
Thread innerThread = new Thread(task);
// daemon thread
innerThread.setDaemon(true);
innerThread.start();
try {
// wait until task finished
innerThread.join();
finished = true;
} catch (InterruptedException e) {
System.out.println("execute thread is interrupted");
//
}
}
}; // new
executeThread.start(); // runnable
}
/**
* 关闭执行线程
* @param milliSeconds 最长等待时间
*/
public void shutdown(long milliSeconds) {
long start = System.currentTimeMillis();
while(!finished) {
if (System.currentTimeMillis() - start >= milliSeconds) {
executeThread.interrupt();
break;
}
try {
TimeUnit.MICROSECONDS.sleep(10);
} catch (InterruptedException e) {
System.out.println(Thread.currentThread().getName() + "线程被打断");
break;
}
}
}
}
public static void main(String[] args) throws InterruptedException {
ThreadService threadService = new ThreadService();
// 执行一个死循环,3s后关闭
threadService.execute(() -> {
while (true) {
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
//
}
System.out.println("a very slow request");
}
});
long begin = System.currentTimeMillis();
threadService.shutdown(3000);
long end = System.currentTimeMillis();
System.out.println("elapsed time:" + (end - begin));
System.out.println("===================================");
// 执行一个10s的任务,但只等待3s
threadService.execute(() -> {
System.out.println("a very slow request");
try {
TimeUnit.SECONDS.sleep(10);
} catch (InterruptedException e) {
//
}
});
begin = System.currentTimeMillis();
threadService.shutdown(3000);
end = System.currentTimeMillis();
System.out.println("elapsed time:" + (end - begin));
System.out.println("===================================");
// 执行一个2s的任务,设置了等待4s,实际执行花了2s的时间
threadService.execute(() -> {
System.out.println("a very slow request");
try {
TimeUnit.SECONDS.sleep(2);
} catch (InterruptedException e) {
//
}
});
begin = System.currentTimeMillis();
threadService.shutdown(4000);
end = System.currentTimeMillis();
System.out.println("elapsed time:" + (end - begin));
}