Java并发编程之线程之间的共享与协作(一)

本文探讨了在多线程环境中如何使用wait和notify方法实现线程间的协作,通过一个汽车打蜡和抛光的实例,展示了如何确保线程安全并实现线程间正确有序的执行。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

共享资源的安全

使用线程运行多个任务时,可以通过加锁(互斥)来保证共享资源的安全。jdk5以后主要有两种方式,synchronized和lock。

wait和notify

在保证线程安全访问共享资源后,我们要思考,多个线程之间的协作的问题。

比如我们生活中的炒菜,炒菜之前要把菜切好,并且把相关的调料准备好,才能开始炒菜。这样,线程之间就有了依赖关系。

java里面提供了wait和notify来实现线程的协作。

wait等待线程里的某个条件发生变化,而改变这个条件超出了这个线程的能力。通常,要由另一个线程来改变。

notify主要功能是唤醒在等待种的线程。

比如上面炒菜,同时启动了炒菜线程和切菜线程,但是炒菜线程启动要,要等待切菜线程执行完,然后通知炒菜线程,炒菜线程才会接着执行。

wait和sleep的区别

  • wait期间锁是释放的,而sleep是不会释放任务资源。

简单线程协作的示例

两个任务:一个任务将腊涂在Car上,一个是抛光它。抛光任务在涂蜡任务完成之前是不能执行的,而涂蜡任务在另一次涂蜡之前,要等待抛光完成。

public class Car {
    /**
    * 标识位
    */
    private boolean waxOn = false;
    

    public synchronized void waxed(){
        //修改标识位为true,表示可以打蜡了
        waxOn = true;
        //唤醒打蜡的线程
        notify();
    }

    public synchronized void buffed(){
        //修改表示为false,表示可以抛光了
        waxOn = false;
        //唤醒抛光线程
        notify();
    }

    public synchronized void waitingToWax() throws InterruptedException{
        //当waxOn为false的时候,打蜡线程阻塞
        if(waxOn == false){
            wait();
        }
    }

    public synchronized void waitingToBuffed()throws InterruptedException{
        //当waxOn为true的时候,抛光线程阻塞
        if(waxOn == true){
            wait();
        }
    }
}

/**
 * @Auther: allen
 * @Date: 2019/10/13 14:52
 * @Description:打蜡线程
 */
public class WaxOn implements Runnable{
    private Car car;

    public WaxOn(Car car) {
        this.car = car;
    }

    public void run() {
        try {
            while (!Thread.interrupted()) {
                System.out.println("Wax On!");
                TimeUnit.MILLISECONDS.sleep(200);
                //通知涂蜡结束,并且阻塞抛光线程
                car.waxed();
                car.waitingToBuffed();
            }
        } catch (Exception e) {
            System.out.println("WaxOn interrupted.")
        }
    }
}

/**
 * @Auther: allen
 * @Date: 2019/10/13 14:55
 * @Description:抛光线程
 */
public class WaxOff implements Runnable{
    private Car car ;

    public WaxOff(Car car) {
        this.car = car;
    }

    public void run() {

        try {
            while (!Thread.interrupted()){
                System.out.println("Wax off!");
                TimeUnit.MILLISECONDS.sleep(200);
                //通知抛光结束,并且阻塞打蜡线程
                car.buffed();
                car.waitingToWax();
            }
        } catch (Exception e) {
            System.out.println("WaxOff interrupted.")
        }
    }
}

/**
 * @Auther: allen
 * @Date: 2019/10/13 14:57
 * @Description:
 */
public class WaxOnMatic {

    public static void main(String[] args) {
        ExecutorService exec = Executors.newCachedThreadPool();

        Car car = new Car();
        exec.execute(new WaxOn(car));
        exec.execute(new WaxOff(car));

        try {
            TimeUnit.MILLISECONDS.sleep(5000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }

        exec.shutdownNow();
    }
}

执行结果:WaxOn和WaxOff是交替输出。

Wax On!Wax off!Wax off!Wax On!Wax off!Wax On!Wax off!
Wax On!Wax off!Wax On!Wax off!Wax On!Wax off!Wax On!
Wax off!Wax On!Wax off!Wax On!Wax off!Wax On!Wax off!
Wax On!Wax off!Wax On!Wax off!Wax On!
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值