码迷,mamicode.com
首页 > 编程语言 > 详细

【线程间通信:等待唤醒机制】

时间:2018-09-02 20:31:54      阅读:164      评论:0      收藏:0      [点我收藏+]

标签:oid   student   cat   cpu   生产者消费者   star   package   定义   sync   

在线程安全解决之后,还是一样存在着如下的问题:

A:如果消费者先抢到CPU的执行权,就会去消费数据,但是现在的数据是默认值,没有意义,应该等着数据有意义,再消费。

B:如果生产者先抢到CPU的执行权,就会去生产数据,但是呢,它生产完数据后,还继续拥有执行权,它又继续产生数据。这是有问题的,它应该等着消费者把数据消费掉,然后再生产。

正常的思路:

A:生产者:先看是否有数据,有就等待,没有就生产,生产完后通知消费者来消费数据。

B:消费者:先是是否有数据,有就消费,没有就等待,通知生产者生产数据。

为了处理这样的问题,JAVA就提供了一种机制,等待唤醒机制。

等待唤醒: Object 类中提供了三个方法:

  wait():等待

  notify():唤醒单个线程

  notifyAll():唤醒所有线程

为什么这些方法不定义在Thread类中呢?

  这些方法的调用必须通过锁对象调用,要所有锁对象都可以调用的话,方法就应该在他们共有的父类上,也就是Object类。

 

例子:线程间通信:生产者消费者(等待唤醒机制)

package com.test;

public class Student {

    String name;
    int age;
    boolean isTrue;

    public synchronized void set(String name, int age) {
        /**如果有数据,就等待*/
        if (this.isTrue) {
            try {
                this.wait();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
        /**设置数据*/
        this.name = name;
        this.age = age;
        /**修改标记*/
        this.isTrue = true;
        this.notify();
    }

    public synchronized void get() {
         /**如果没有数据,就等待*/
        if (!this.isTrue) {
            try {
                this.wait();
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
         /**获取数据*/
        System.out.println(this.name + "---" + this.age);
         /**修改标记*/
        this.isTrue = false;
        this.notify();
    }

}
package com.test;

public class SetThread implements Runnable {

    private Student s;
    private int x = 0;

    public SetThread(Student s) {
        this.s = s;
    }

    @Override
    public void run() {
        while (true) {

            if (x % 2 == 0) {
                s.set("叶胖子", 27);
            } else {
                s.set("王瘦子", 31);
            }
            x++;

        }
    }
}
package com.test;

public class GetThread implements Runnable {

    private Student s;

    public GetThread(Student s){
        this.s = s;
    }

    @Override
    public void run() {
        while (true){
            s.get();
        }
    }

}
package com.test;

public class StudentTest {

    public static void main(String[] args) {

        Student s = new Student();

        SetThread st = new SetThread(s);
        GetThread gt = new GetThread(s);

        Thread t1 = new Thread(st);
        Thread t2 = new Thread(gt);

        t1.start();
        t2.start();

    }

}

 

【线程间通信:等待唤醒机制】

标签:oid   student   cat   cpu   生产者消费者   star   package   定义   sync   

原文地址:https://www.cnblogs.com/zuixinxian/p/9574749.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!