用JDK1.5的类库Lock锁和lock锁上获得的多个Condition对象。就可以1对1。
下面的代码是我自己写的练习。你可以看下。
package cn.basic;
//线程同步和通信
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;
public class MultiThreadShareData {
private String name=null;
private final Lock lock=new ReentrantLock();
private final Condition con1=lock.newCondition();
private final Condition con2=lock.newCondition();
private boolean flag=false;
private int count=0;//用于统计生产消费的商品总数
private int cnt1=0; //用于存储生产商品数
private int cnt2=0;//用于存储消费商品数
private int thread1=0;//存储开启的生产线程数
private int thread2=0;//存储开启的消费线程数
public static void main(String[] args) {
MultiThreadShareData mtsd= new MultiThreadShareData();
mtsd.proAndCon(4, 5, 100);
}
public void proAndCon(int proThread,int conThread,int cnt ){
produceOn(proThread,cnt);
consumerOn(conThread,cnt);
}
//开启生产线程,参数为线程个数,要生产的商品数
private void produceOn(int thread,int cnt){
if(thread<=0||cnt<=0){
return;
}
this.cnt1=cnt;
this.thread1=thread;
ThreadPro t1=new ThreadPro();
for(int i=0;i<thread;i++ ){
new Thread(t1).start();
}
}
//开启消费线程,参数为线程个数,要消费的商品数
private void consumerOn(int thread,int cnt){//线程数,以及要生产的个数
if(thread<=0||cnt<=0){
return;
}
if(cnt>cnt1){
throw new RuntimeException("消费商品个数不能大于生产的个数");
}
this.cnt2=cnt;
this.thread2=thread;
ThreadCon t2=new ThreadCon();
for(int i=0;i<thread;i++){
new Thread(t2).start();
}
}
//每次生产商品过程,字符串表示
private void initProduce(String name) throws InterruptedException{
lock.lock();
try{
while(flag){
con1.await();
}
this.name=name+"--"+(count++);
System.out.println(Thread.currentThread().getName()+"生产---"+this.name);
flag=true;
con2.signal();
}
finally{
lock.unlock();
}
}
//每次消费商品过程,字符串表示
private void initConsumer() throws InterruptedException{
lock.lock();
try{
while(!flag){
con2.await();
}
System.out.println(Thread.currentThread().getName()+"----消费--------"+this.name);
flag=false;
con1.signal();
}
finally{
lock.unlock();
}
}
//对多线程生产提供支持
private class ThreadPro implements Runnable{
@Override
public void run() {
int x= Math.round((cnt1*1f)/thread1);
for(int j=1;j<=x;j++){
try {
initProduce("haha");
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
//对多线程消费提供支持
private class ThreadCon implements Runnable {
@Override
public void run() {
int x= Math.round((cnt2*1f)/thread2);
for(int j=1;j<=x;j++){
try {
initConsumer();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
}
|