状态图:
方法说明:
run 线程运行的主体
yield() 放弃当前的时间片进入可运行状态,可以被再次选中
start() 线程进入可运行阶段
sleep(), 阻塞一定的时间,会持有锁
t2.join() 等待t2线程运行结束,会持有锁,有可能会死锁
wait() 锁对象的方法,持有锁对象的线程释放锁,进入阻塞队列等待notify
notify() 锁对象的方法,唤醒一个该锁对象阻塞队列中的线程
notifyAll() 锁对象的方法,唤醒所有该锁对象阻塞队列中的线程
wait , notify, notifyAll
class SynClass{ public void execute(){ System.out.println(Thread.currentThread().getName()); } }
final SynClass sc = new SynClass(); Thread[] ts = new Thread[10]; for (int i = 0; i < 10; i++) { ts[i] = new Thread("thread" + i){ public void run() { synchronized (sc) { try { sc.wait(); sc.execute(); } catch (InterruptedException e) { e.printStackTrace(); } } }; }; } for (Thread t : ts) { t.start(); } TimeUnit.SECONDS.sleep(1); synchronized (sc) { sc.notify(); sc.notify(); } while(true);
会打印:
thread1
thread0
如果把其中的sc.notify()换为notifyAll()则会打印出所有的线程。
interrupt
在阻塞的方法比如wait() 或者sleep()中会有while(interruped()) throws InterruptedException()方法,
interrupt()方法会设置状态为打断状态
interrupted()方法如果是打断状态返回true,同时设置打断状态为false;
生产者消费者
public class Storage { private String[] products = new String[2]; private int index = -1; public synchronized void produce(String product) throws InterruptedException{ while(index == products.length - 1){ System.out.println("超出上限无法生产"); this.wait(); } products[++index] = product; System.out.println("生产了" + product); this.notify(); } public synchronized String consume() throws InterruptedException{ while(index == -1){ System.out.println("没有库存了"); this.wait(); } this.notify(); return products[index--]; } public static void main(String[] args) { final Storage s = new Storage(); new Thread(){ public void run() { while(true){ try { System.out.println("消费了" + s.consume()); } catch (InterruptedException e) { e.printStackTrace(); } try { TimeUnit.MILLISECONDS.sleep(new Random(1000).nextLong()); } catch (InterruptedException e) { e.printStackTrace(); } } }; }.start(); new Thread(){ public void run() { while(true){ try { s.produce("product" + new Random().nextInt(100)); } catch (InterruptedException e) { e.printStackTrace(); } try { TimeUnit.MILLISECONDS.sleep(new Random(1000).nextLong()); } catch (InterruptedException e) { e.printStackTrace(); } } }; }.start(); while(true); } }一个线程生产,一个线程消费。
生产超出上限则wait消费,没超出则进行生产,开始生产了就应该通知消费者可以消费了。
消费线程没有商品则wait生产,有商品就消费,同时通知生产者可以继续生产了。