一 线程状态
1. NEW
线程刚刚被创建时的状态。
2. RUNNABLE
NEW状态的线程调用了start()方法来启动后可能处于的状态。如果线程满足运行的状态,但还没有得到CPU调度,则处于此状态。
3. RUNNING
正在运行的线程状态。
4. TERMINATED
线程运行结束的状态。
5. BLOCKED
调用了start方法,但线程需要运行的某些资源没有得到满足时会处于BLOCKED状态。
6. WAITING & TIMED_WAITING
调用了wait方法的线程处于WAITING状态。WAITING状态的线程,可以通过notify方法唤醒。TIMED_WAITING除了可以通过notify唤醒外,还可以一个等待时间,超过了这个时间,线程也会自动唤醒。
二 线程运行方式
Thread t1=new Thread();
t1.run(); //不能开启线程,只是像普通代码一样在当前线程执行run里面的逻辑
t1.start(); //会开启新的线程
三 线程基本操作
1. Thread.stop();
不推荐使用。它会释放所有monitor,强行中断线程。
对于线程中有多条语句在执行,强行中断可能造成部分数据更新,部分数据没有更新,造成数据不一致
2. interrupt
public void Thread.interrupt() // 中断线程
public boolean Thread.isInterrupted() // 判断是否被中断
public static boolean Thread.interrupted() // 判断是否被中断,并清除当前中断状态
public void run(){
while(true){
Thread.yield();
}
}
t1.interrupt(); // 这种方式不会对t1造成任何影响,因为只是通知了t1,但没有告诉t1怎么做
public void run(){
while(true){
// 告知线程interrupt后如何做
if(Thread.currentThread().isInterrupted()){
System.out.println("Interruted!");
break;
}
Thread.yield();
}
}
3. suspend/resume
suspend 挂起,中断线程的执行。resume恢复线程的执行。
不建议使用。suspend()不会释放锁,如果加锁发生在resume()之前 ,则死锁发生。
4. 等待线程结束(join)和谦让(yeild)
public class JoinMain {
public volatile static int i=0;
public static class AddThread extends Thread{
@Override
public void run() {
for(i=0;i<10000000;i++);
}
}
public static void main(String[] args) throws InterruptedException {
AddThread at=new AddThread();
at.start();
at.join(); // 等待at线程执行完毕,再往下执行
System.out.println(i);
}
}
yeild:把自己拥有的资源释放掉,再重新去竞争(有可能还会再次获取到资源)。
5. wait/notify
不建议使用,因为这两个方法是系统调用的。开发者调用的话,可能不会被系统执行,起不到作用。
wait:线程会释放执行权,且释放锁
6. 守护线程
在后台默默地完成一些系统性的服务,比如垃圾回收线程、JIT线程就可以理解为守护线程。
当一个Java应用内,只有守护线程时,Java虚拟机不会等待守护线程结束,就自然退出。
Thread t=new DaemonT();
t.setDaemon(true);
t.start();
7. 线程优先级
Thread high=new HightPriority();
LowPriority low=new LowPriority();
high.setPriority(Thread.MAX_PRIORITY);
low.setPriority(Thread.MIN_PRIORITY);
low.start();
high.start();
高优先级的线程更容易再竞争中获胜,并不是一定!!
8. 线程同步
synchronized
– 指定加锁对象:对给定对象加锁,进入同步代码前要获得给定对象的锁。
– 直接作用于实例方法:相当于对当前实例加锁,进入同步代码前要获得当前实例的锁。
– 直接作用于静态方法:相当于对当前类加锁,进入同步代码前要获得当前类的锁。
9. sleep
sleep也可以由notify唤醒。即使睡眠了,仍持有锁,不会释放执行权。