1.ReentrantLock实现
/**
* 描述: 一个初始值为0的变量,两个线程对其交替操作,一个加一个减
*
* @author [email protected]
* @create 2020/2/22 11:55
* @since 2.16.3
*/
class ShareData{
private int number = 0;
private Lock lock = new ReentrantLock();
private Condition condition = lock.newCondition();
public void increment() throws Exception{
lock.lock();
try{
// 1判断
while(number != 0){
// 等待,不能生产
condition.await();
}
number++;
System.out.println(Thread.currentThread().getName()+"\t"+number);
// 通知唤醒
condition.signalAll();
}catch (Exception e){
e.printStackTrace();
}finally {
lock.unlock();
}
}
public void decrement() throws Exception{
lock.lock();
try{
// 1判断
while(number == 0){
// 等待,不能生产
condition.await();
}
number--;
System.out.println(Thread.currentThread().getName()+"\t"+number);
// 通知唤醒
condition.signalAll();
}catch (Exception e){
e.printStackTrace();
}finally {
lock.unlock();
}
}
}
public class ProConsumer_ReentrantLockDemo {
public static void main(String[] args) {
ShareData shareData = new ShareData();
new Thread(()->{
for(int i=1;i<=5;i++){
try{
shareData.increment();
}catch (Exception e){
e.printStackTrace();
}
}
},"AA").start();
new Thread(()->{
for(int i=1;i<=5;i++){
try{
shareData.decrement();
}catch (Exception e){
e.printStackTrace();
}
}
},"BB").start();
}
}
2.BlockingQueue实现
class MyResource{
private volatile boolean FLAG = true;
private AtomicInteger atomicInteger = new AtomicInteger();
private BlockingQueue<String> blockingQueue = null;
// 构造方法注入
public MyResource(BlockingQueue<String> blockingQueue){
this.blockingQueue = blockingQueue;
System.out.println(blockingQueue.getClass().getName());
}
public void myProd() throws Exception{
String data = null;
boolean retValue;
while (FLAG){
data = atomicInteger.incrementAndGet()+"";
retValue = blockingQueue.offer(data,2L, TimeUnit.SECONDS);
if(retValue){
System.out.println(Thread.currentThread().getName()+"\t 插入队列"+data+"成功");
}else {
System.out.println(Thread.currentThread().getName()+"\t 插入队列"+data+"失败");
}
TimeUnit.SECONDS.sleep(1);
}
System.out.println(Thread.currentThread().getName()+"\t 大老板叫停了,表示FLAG=false,生产动作结束");
}
public void myConsumer() throws Exception{
String result = null;
while (FLAG){
result = blockingQueue.poll(2L,TimeUnit.SECONDS);
if(null == result || result.equalsIgnoreCase("")){
FLAG = false;
System.out.println(Thread.currentThread().getName()+"\t 超过2秒钟没有取到蛋糕,消费退出");
System.out.println();
return;
}
System.out.println(Thread.currentThread().getName()+"\t 消费队列"+result+"成功");
}
}
public void myStop() throws Exception{
this.FLAG=false;
}
}
public class ProConsumer_BlockQueueDemo {
public static void main(String[] args) throws Exception{
MyResource myResource = new MyResource(new ArrayBlockingQueue<>(3));
new Thread(()->{
System.out.println(Thread.currentThread().getName()+"\t 生产者线程启动");
try {
myResource.myProd();
} catch (Exception e) {
e.printStackTrace();
}
},"Prod").start();
new Thread(()->{
System.out.println(Thread.currentThread().getName()+"\t 消费者线程启动");
try {
myResource.myConsumer();
} catch (Exception e) {
e.printStackTrace();
}
},"Consumer").start();
// 暂停一会线程
TimeUnit.SECONDS.sleep(5);
System.out.println();
System.out.println();
System.out.println("5秒钟时间到,大老板main线程叫停,活动结束");
myResource.myStop();
}
}