今天学习了线程的交互,什么叫线程交互?如何交互?
线程交互:通俗的说就是线程之间的交互通知。
如何交互:这里使用notify(),wait()。
notify(),是线程唤醒正在等待的当前这个同步对象的线程。
wait(), 是线程等待,同时暂时释放正在占有的对象。(注意”占有“,是不是很熟悉,表示它是和线程同步一起的)。
列子:有两个线程,处理同一个英雄。一个加血,一个减血。
减血的线程,发现血量<=1,就停止减血,直到加血的线程为英雄加了血>=10,才可以继续减血。
hero.java代码:
public class Hero {
private StringBuffer name; //人物姓名
private float hp; //生命值
private int damage; //伤害值
public Hero(StringBuffer name, float hp, int damage) {
this.name = name;
this.hp = hp;
this.damage = damage;
}
public Hero() { }
public StringBuffer getName() {
return name;
}
public float getHp() {
return hp;
}
public int getDamage() {
return damage;
}
/*使用synchronized 进行修饰,表示方法是线程安全*/
//加血
public synchronized void recovery() {
if(hp>=10){
System.out.println("补充完毕!");
System.out.printf("recovery:当前hero:%s,hp值为%.0f%n", name, hp);
// 通知那些等待在this对象上的线程,可以醒过来了
this.notify();
}
else {
this.hp =this. hp + 2;
}
}
//攻击,减血
public synchronized void attack() {
if (hp<=1){
System.out.println("hp值 已经不足,请补充");
try {
//当hp值小于等于 1 时,等待。
this.wait();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
this.hp = this.hp -3;
System.out.printf("attack:当前hero:%s,hp值为%.0f%n", name, hp);
}
}
TestThread.java 代码:
public class WaitAndNotify {
public static void main(String[] args) {
final Hero h1 = new Hero(new StringBuffer("达摩"), 18.0f, 150);
Thread t1 = new Thread(){
public void run(){
while(true){
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
//减血
h1.attack();
}
}
};
t1.start();
Thread t2 = new Thread(){
public void run(){
while(true){
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
//加血
h1.recovery();
}
}
};
t2.start();
}
}
结果:
以上就是写的代码了,里面最主要的是 wait(),notify()。wait()线程暂时释放对象,进行等待,notify()进行唤醒正在等待的当前这个同步对象的线程。
补充:
关于notify()与notifyAll():
1,其实wait(),notify()不是Tread里面的方法,他们来自于Object。所有的对象(Object)都可以被称为同步对象,所以也可以说它们是同步对像上的方法。
2,notify(),是提醒或者说是唤醒 当前占有该同步对象的线程,notifyAll()是唤醒 当前占有该同步对象的所有线程 。