多线程初探(八)

来源:互联网 发布:酷家乐云设计软件下载 编辑:程序博客网 时间:2024/05/24 23:16
package com.liujunhua.ith02;/** * 线程的等待唤醒机制 * 两个线程对同一资源进行操作,为保证两者操作资源的独立性,出现了等待唤醒机制。 * 1.Input线程负责对变量赋值,为了避免在Input在具有CPU执行权时,进行重复的变量赋值动作, *   当首次赋值后进行标记,当线程再次赋值的时候,先对标记进行判断,若已经赋值并且该数值还没有 *   被Output输出,Input线程就等待。即放弃执行权。 * 2.当Input等待的时候Output就会获得CPU执行权,就会执行相应的输出操作。当完成输出操作后,它将标记为已经操作状态。 *   当下次执行的时候,如果发现标记已经输出,并且Input没有进行新的赋值,那么就会进入等待状态。 *  * 从而实现了等待唤醒机制。 *  * wait(); * notify(); * notifyAll(); *  * 这些方法都使用在同步中,因为要对持有监视器(锁)的线程进行操作。 * 所以要使用在同步中,因为只有同步才具有锁。 *  * 但是为什么这些操作线程的方法要定义在Object类中呢? *  * 那是因为这些方法在操作同步中的线程是,都必须要标识他们所操作线程的锁, * 只有同一个锁上的被等待的线程,可以被同一个锁上的notify唤醒。 *  * 也就是说,等待和唤醒必须是同一个锁。 *  * 而锁可以是任意对象,所以可以被任意对象调用的方法定义在object类中。 */public class Demo01 {public static void main(String[] args){Res r = new Res();Input in = new Input(r);Output out = new Output(r);Thread t1 = new Thread(in);Thread t2 = new Thread(out);t1.start();t2.start();}}class Res {private String name;private String sex;private boolean flag = false;public String getName() {return name;}public void setName(String name) {this.name = name;}public String getSex() {return sex;}public void setSex(String sex) {this.sex = sex;}public boolean isFlag() {return flag;}public void setFlag(boolean flag) {this.flag = flag;}public void print(){System.out.println(this.name+"........"+this.sex);}}/** * 这里线程锁的创建很有技巧性,如果仅仅是简单的obj对象,肯定是不行的,因为一个obj不可能在两个类里面都可以用。 * 但此时又需要两个同步代码块用同一个线程锁,这里便采用了两个线程共同操作的Res对象作为线程锁,很好的解决了线程的安全问题。 */class Input implements Runnable {private Res r;Input(Res r) {this.r = r;}@Overridepublic void run() {// TODO Auto-generated method stubint mark = 0;while (true) {synchronized (r) {if(r.isFlag())try {r.wait();} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}if (mark == 0) {r.setName("mike"); r.setSex("man");} else {r.setName("丽丽"); r.setSex("女女");}mark = (mark + 1) % 2;r.setFlag(true);r.notify();}}}}class Output implements Runnable {private Res r;Output(Res r) {this.r = r;}@Overridepublic void run() {// TODO Auto-generated method stubwhile (true) {synchronized (r) {if(!r.isFlag()){try {r.wait();} catch (InterruptedException e) {// TODO Auto-generated catch blocke.printStackTrace();}}r.print();r.setFlag(false);r.notify();}}}}

0 0
原创粉丝点击