1. new 新建状态
使用new创建Thread对象时,线程并不处于执行状态,因为没有调用start()方法启动线程。 通过调用start()方法让线程进入runnable状态。
2. runnable 可运行状态
进入runnable 状态的线程不会立即执行,只是具备了执行的资格,并没有真正执行起来,实在等待CPU的调度。
3 running 运行状态
表示线程正在执行中,状态可以发生如下转换:
1. 直接进入terminated状态。
2. 进入blocked状态,比如调用sleep(),或者wait()而加入waitSet中;进入某个阻塞的IO操作;或者获取某个锁资源,加入到该锁的阻塞队列中。
3. 由于CPU的调度轮询使线程放弃执行,进入runnable状态。
4. 线程调用yield()方法,放弃CPU执行权,进入runnable状态。
4. blocked 阻塞状态
1. 直接进入terminated状态。
2. 线程阻塞的操作结束;完成指定时间休眠;waitSet中的线程被notify/notifyall唤醒;获取到某个锁资源;线程在阻塞过程中被打断,比如调用了interrupt()方法;以上都会使线程进入runnable状态。
5. terminated 终止状态
线程的一个最终状态,该状态不会切换到任何状态,意味着线程的整个生命周期结束。
1. 线程正常运行结束。
2. 线程运行出错意外结束。
3. JVM Crash 导致所有的线程结束。
start方法解析
//新建线程threadStatus 为0 ,volatile 关键字能保证不同线程间对共享变量的可见性。
private volatile int threadStatus = 0;
public synchronized void start() {
if (threadStatus != 0)
throw new IllegalThreadStateException();
group.add(this);
boolean started = false;
try {
start0();
started = true;
} finally {
try {
if (!started) {
group.threadStartFailed(this);
}
} catch (Throwable ignore) {
/* do nothing. If start0 threw a Throwable then
it will be passed up the call stack */
}
}
}
- 线程启动时的start()方法调用了start0()方法,由start0调用线程的run方法实现线程的功能。(也就是strart与run的关系)
- strat()方法会拒绝线程的多次启动,多次启动会抛出IllegalThreadStateException,启动的线程会被加入到ThreadGroup中。
抛出IllegalThreadStateException异常的情况:
- 线程重复启动
Thread t = new Thread(){
@Override
public void run() {
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
};
t.start();
t.start();
- 启动一个已经结束的线程
Thread t = new Thread(){
@Override
public void run() {
try {
TimeUnit.SECONDS.sleep(1);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
};
t.start();
try {
//休眠是确保线程生命周期结束
TimeUnit.SECONDS.sleep(3);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
t.start();
```java
Exception in thread "main" java.lang.IllegalThreadStateException
at java.lang.Thread.start(Unknown Source)
at semaphore.ThreadTest.main(ThreadTest.java:34)
重写Thread类的run()和实现Runnable接口的run()区别
Thread类的run()时不能共享,,而使用Runable接口的则可以实现这一点,使用同一个Runable接口构造不同的Thread实列。
Thread与Runnable
Thread负责线程本身相关的职责和控制,Runnable则负责逻辑执行单元的部分(run方法)。