生產者消費者問題(附代碼)與線程池配置

分析:
1.在庫存爲滿時,生產者纔可以生產,同理有庫存時消費者纔可以消費,否則就等待。
2.當消費者消費完,活着生產者生產完  應該去通知對方,並釋放對象鎖
3.對象的wait方法,wait方法的作用是釋放當前線程的所獲得的鎖,
4.notifyAll() 方法, 通知(喚醒)該對象上其他等待線程,使得其繼續執行。

5.synchronized關鍵字只作用與當前實例對象的方法。

 

package com.producer.consumer;

public class MainTest {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
        /**
         * 初始化數據池和一個生產線程A 兩個消費線程D E
         * 
         */
		BufferData data = new BufferData();
		new Thread(new Producer(data, "A")).start();
		// new Thread(new Producer(data,"B")).start();
		// new Thread(new Producer(data,"C")).start();
		new Thread(new Consumer(data, "D")).start();
		new Thread(new Consumer(data, "E")).start();
	}

}

運行log
生產者

 

package com.producer.consumer;

public class Producer implements Runnable {
	public String mThreadName;
	public BufferData mData;

	public Producer(BufferData data, String threadName) {
		this.mThreadName = threadName;
		this.mData = data;
	}

	@Override
	public void run() {
		// TODO Auto-generated method stub
		for (int i = 0; i < 10; i++) {
			try {
				Thread.sleep(1000);
			} catch (InterruptedException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			//隨機生產存入 數據池
			int random = (int) (Math.random() * 1000 + 1);
			mData.toProducer(random);
			System.out.println(mThreadName + "線程存入:" + random);
		}

	}

}

 


消費者

package com.producer.consumer;

public class Consumer implements Runnable {
	public String mThreadName;
	public BufferData mBufferData;

	public Consumer(BufferData data, String threadName) {
		this.mBufferData = data;
		this.mThreadName = threadName;
	}

	@Override
	public void run() {
		// TODO Auto-generated method stub
		for (int i = 0; i < 10; i++) {
			try {
				Thread.sleep(1000);
			} catch (InterruptedException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
			int value = mBufferData.toConsumer();
			System.out.println(mThreadName + "線程消費:" + value);

		}
	}

}

 

線程基礎知識點

import java.util.concurrent.Future;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicInteger;
/**
 * 線程池配置參數說明
 * 第一個參數核心線程數 併發的
 * 第二個參數 非核心線程數=核心線程數+緩存隊列Runnable數 
 * 第三個參數 非核心線程超時時間
 * 第四個參數 時間單位
 * 第五個參數緩存隊列
 *    ArrayBlockingQueue 大小固定的 順序執行
 *    LinkedBlockingQueue 無限制的 順序執行
 *    PriorityBlockingQueue 優先級執行
 *    SynchronizedQueue 同步執行 併發 不緩存
 * 第六個線程工廠
 * @author zwh
 *
 */
public class LocalThreadPool {
	private static LocalThreadPool mInstance;
	private ThreadPoolExecutor threadPool;
	private static int MAX_CORE_NUMBER = Runtime.getRuntime().availableProcessors();
	private LocalThreadPool() {
		threadPool = new ThreadPoolExecutor(MAX_CORE_NUMBER, 10, 60, TimeUnit.SECONDS,
				new LinkedBlockingQueue<Runnable>(), new ThreadFactory() {
					AtomicInteger auto = new AtomicInteger(0);
					@Override
					public Thread newThread(Runnable r) {
						// TODO Auto-generated method stub
						Thread thread = new Thread(r, "crate-thread-" + auto.incrementAndGet());
						System.out.println("create thread:" + thread.getName());
						return thread;
					}

				});
		threadPool.allowCoreThreadTimeOut(true);
	}

	public static LocalThreadPool getInstance() {
		if (mInstance == null) {
			synchronized (LocalThreadPool.class) {
				if (mInstance == null) {
					mInstance = new LocalThreadPool();
				}
			}

		}
		return mInstance;
	}

	public Future<?> submit(Runnable runnable) {
		return threadPool.submit(runnable);
	}

	public int count() {
		return threadPool.getActiveCount();
	}

	public void destory() {
		threadPool.shutdown();
	}

}

 

 

 

 

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章