经典多线程Java实例 生产者与消费者

    生产者-消费者问题是一个经典的进程同步问题,该问题最早由Dijkstra提出,用以演示他提出的信号量机制。在同一个进程地址空间内执行的两个线程。生产者线程生产物品,然后将物品放置在一个空缓冲区中供消费者线程消费。消费者线程从缓冲区中获得物品,然后释放缓冲区。当生产者线程生产物品时,如果没有空缓冲区可用,那么生产者线程必须等待消费者线程释放出一个空缓冲区。当消费者线程消费物品时,如果没有满的缓冲区,那么消费者线程将被阻塞,直到新的物品被生产出来。

代码如下:

Producer.java 生产者

package factory;

class Producer extends Thread {
    private Factory sharedLocation;

    public Producer( Factory shared) {
        super ( "Producer" ) ;
        sharedLocation = shared;
    }

    public void run ( ) {
        for ( int count = 1; count < = 10; count + + ) {
            try {
                Thread . sleep ( ( int ) ( Math . random ( ) * 2000) ) ;
                sharedLocation. set ( count ) ;
            } catch ( InterruptedException e) {
                e. printStackTrace ( ) ;
            }
        }
        System . out. println ( getName ( ) + " 生产结束" ) ;
    }
}




Consumer.java 消费者

package factory;

public class Consumer extends Thread {
    private Factory sharedLocation;

    public Consumer( Factory shared) {
        super ( "Consumer" ) ;
        sharedLocation = shared;
    }

    public void run ( ) {
        int sum = 0;
        for ( int count = 1; count < = 10; count + + ) {
            try {
                Thread . sleep ( ( int ) ( Math . random ( ) * 3000) ) ;
                //消费商品

                sum + = sharedLocation. get ( ) ;

            } catch ( InterruptedException e) {
                e. printStackTrace ( ) ;
            }
        }
        System . out. println ( getName ( ) + " 消费总数 " + sum + " 消费结束" ) ;

    }
}




Factory.java 工厂接口

package factory;

public interface Factory {
    public void set ( int value ) ;
    public int get ( ) ;
}




FactorySynchronizedImpl.java 工厂实现

package factory;

/**
 * 注意get set两个方法使用同一把锁
 */

public class FactorySynchronizedImpl implements Factory {
    private int item = - 1;
    private int sign = 0; // >0是是可以买 ==0是不能卖

    private static final int maxSize = 3; // 最大库存


    public synchronized void set ( int value ) {
        String name = Thread . currentThread ( ) . getName ( ) ;
        while ( sign > = maxSize) {
            try {
                displayState( "产品 " + name + " 库存已满!等待..." ) ;
                wait ( ) ;
            } catch ( InterruptedException e) {
                e. printStackTrace ( ) ;
            }
        }
        item = value ;
        + + sign ;
        displayState( name + " 生产 " + item ) ;
        // 唤醒同锁线程

        notify ( ) ;
    }

    public synchronized int get ( ) {
        String name = Thread . currentThread ( ) . getName ( ) ;
        while ( sign < = 0) {
            try {
                displayState( "无产品 " + name + " 等待" ) ;
                wait ( ) ;
            } catch ( InterruptedException e) {
                e. printStackTrace ( ) ;
            }
        }
        - - sign ;
        displayState( name + " 买 " + item ) ;
        // 唤醒同锁线程

        notify ( ) ;
        return item ;
    }

    public void displayState( String operation ) {
        System . out. println ( "操作序号:" + item + "/t/t库存:" + sign + "/t" + operation ) ;
    }
}




Test.java 运行类

package factory;

public class Test {
    public static void main( String args[ ] ) {
        FactorySynchronizedImpl factory = new FactorySynchronizedImpl( ) ;
        System . out. println ( ) ;
        factory. displayState( "初始化" ) ;
        Producer p = new Producer( factory) ;
        Consumer c = new Consumer( factory) ;
        p. start ( ) ;
        c. start ( ) ;
    }
}




    希望大家有所收获!

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值