12、Exchanger

java.util.concurrent

Class Exchanager<V>

 

用于实现两个线程之间元素的交换。每个线程在完成一定的事务后想与另外一个线程交换数据,第一个拿出数据的线程一直等待第一个拿出

数据的线程,直到两个线程都拿出数据,才能进行数据交换。Exchanger对于遗传数学和管道设计应用也许很有用。

 

 1 class FillAndEmpty {
 2    Exchanger<DataBuffer> exchanger = new Exchanger<DataBuffer>();
 3    DataBuffer initialEmptyBuffer = ... 
 4    DataBuffer initialFullBuffer = ...
 5 
 6    class FillingLoop implements Runnable {
 7      public void run() {
 8        DataBuffer currentBuffer = initialEmptyBuffer;
 9        try {
10          while (currentBuffer != null) {
11            addToBuffer(currentBuffer);
12            if (currentBuffer.isFull())
13              currentBuffer = exchanger.exchange(currentBuffer);
14          }
15        } catch (InterruptedException ex) { ... handle ... }
16      }
17    }
18 
19    class EmptyingLoop implements Runnable {
20      public void run() {
21        DataBuffer currentBuffer = initialFullBuffer;
22        try {
23          while (currentBuffer != null) {
24            takeFromBuffer(currentBuffer);
25            if (currentBuffer.isEmpty())
26              currentBuffer = exchanger.exchange(currentBuffer);
27          }
28        } catch (InterruptedException ex) { ... handle ...}
29      }
30    }
31 
32    void start() {
33      new Thread(new FillingLoop()).start();
34      new Thread(new EmptyingLoop()).start();
35    }
36  }

程序分析:

有两个线程,一个是填充数据缓存,一个是消耗数据缓存。两个线程都是通过while语句来对各自的DataBuffer类型的数据进行判断。说明这是一个循环生产与消费的类型。

当填充线程将缓存容器填充满了之后,交到"交易平台"Exchanger;当消费线程从当前的缓存容器中拿取缓存数据直至为空时,就将缓存容器交到"交易平台"Exchanger。

假设消费线程比较早的启动了,此时缓存容器中数据为空,因此它会将其提交到Exchanger,但是此时,消费线程的exchange并不会返回值,而是阻塞于此。当填充线程

将缓存容器填充满,交到Exchanger后,消费线程的exchange会返回消费线程提交到Exchanger的空的缓存容器;与此同时,消费线程从exchange唤醒并返回填充线程

提交到Exchanger的填充好数据的缓存容器。

posted on 2015-06-01 11:48  飞机说之代码也疯狂  阅读(185)  评论(0编辑  收藏  举报