2011년 6월 13일 월요일

JDK 5.0 java.util.concurrent package - 3

3. Exchanger<V> Class
이 클래스는 두 쓰레드 사이의 명확한 객체의 전송에 의한 쓰레드 내에 간단한 통신 방법을 제안한다. Exchanger는 스트림 기반의 쓰레드간 통신(한쪽에서 쓰고 한쪽에서 읽는 방식)을 위한 Piped 스트림을 이용하는 대신, 쓰레드 사이의 one-off(일회성)데이터의 통신을 위한 단일 교환 메소드를 사용한다. Exchanger는 pipe model의 일반적인 대체방법은 아니지만 사용법은 비슷하다.
참고 : Generics 기능
C++에서는 템플릿(Generics)이 존재한다. 자바 1.5에서도 Collection 클래스에 템플릿 기능이 추가되었다.
[jdk1.4]
ArrayList array = new ArrayList();
Iterator iter = array.iterator();
while(iter.hasNext()){
String str = (String)iter.next();
System.out.println(str);
}
아래처럼 컬렉션클래스에 형을 지정하므로써, 실행시에 캐스팅(casting)이 불필요하게 되었다.
[jdk1.5]
List<String> array = new ArrayList<String>();
Iterator<String> iter = array.iterator();
while(iter.hasNext()){
String str = (String)iter.next();
System.out.println(str);
}


아래의 샘플은 Exchanger를 사용해 thread간에 버퍼를 교환하는 클래스 이다. 버퍼를 채우는 thread가 필요에 따라서 새로운 하늘의 버퍼를 취득해, 버퍼를 비우는 thread에 채워진 버퍼를 건네줍니다.
package sun.tips;
import java.util.*;
import java.util.concurrent.*;
public class ExchangerTest {
private static final int FULL = 5;
private static final int COUNT = FULL * 2;
private static final Random random = new Random();
private static volatile int sum = 0;
private static Exchanger<List<Integer>> exchanger =
new Exchanger<List<Integer>>();
private static CountDownLatch stopLatch =
new CountDownLatch(2);
private static List<Integer> initiallyEmptyBuffer;
private static List<Integer> initiallyFillBuffer;
private static class FillingLoop implements Runnable {
public void run() {
List<Integer> currentBuffer = initiallyFillBuffer;
try {
for (int i = 0; i < COUNT; i++) {
if (currentBuffer == null)
break;
Integer item = random.nextInt(100);
System.out.println("Item Added: " + item);
currentBuffer.add(item);
if (currentBuffer.size() == FULL) {
currentBuffer =
exchanger.exchange(currentBuffer);
}
}
} catch (InterruptedException ex) {
System.out.println("Bad exchange on filling side");
}
stopLatch.countDown();
}
}
private static class EmptyingLoop implements Runnable {
public void run() {
List<Integer> currentBuffer = initiallyEmptyBuffer;
try {
for (int i = 0; i < COUNT; i++) {
if (currentBuffer == null)
break;
if (currentBuffer.isEmpty()) {
currentBuffer =
exchanger.exchange(currentBuffer);
}
Integer item = currentBuffer.remove(0);
System.out.println("Item Got: " + item);
sum += item.intValue();
}
} catch (InterruptedException ex) {
System.out.println("Bad exchange on emptying side");
}
stopLatch.countDown();
}
}
public static void main(String args[]) {
initiallyEmptyBuffer = new ArrayList<Integer>();
initiallyFillBuffer = new ArrayList<Integer>();
new Thread(new FillingLoop()).start();
new Thread(new EmptyingLoop()).start();
try {
stopLatch.await();
} catch (InterruptedException ex) {
ex.printStackTrace();
}
System.out.println("Sum of all items is.... " + sum);
}
}


결과
Item Added: 85
Item Added: 81
Item Added: 23
Item Added: 91
Item Added: 64
Item Added: 7
Item Added: 28
Item Added: 60
Item Added: 15
Item Added: 53
Item Got: 85
Item Got: 81
Item Got: 23
Item Got: 91
Item Got: 64
Item Got: 7
Item Got: 28
Item Got: 60
Item Got: 15
Item Got: 53
Sum of all items is.... 507


Exchanger<V> Method
exchange(V x)
다른 thread가 이 교환 포인트에 도달할 때까지 대기해, 지정된 오브젝트를 그 thread에 전송 하고, 상대 오브젝트를 받습니다.
exchange(V x,
long timeout,
TimeUnit unit)
지정된 대기 시간이 경과하지 않는 한, 다른 thread가 이 교환 포인트에 도달할 때까지 대기해, 지정된 오브젝트를 그 thread에 전송 하고, 상대 오브젝트를 받습니다.

댓글 없음:

댓글 쓰기

ETL 솔루션 환경

ETL 솔루션 환경 하둡은 대용량 데이터를 값싸고 빠르게 분석할 수 있는 길을 만들어줬다. 통계분석 엔진인 “R”역시 하둡 못지 않게 관심을 받고 있다. 빅데이터 역시 데이터라는 점을 볼때 분산처리와 분석 그 이전에 데이터 품질 등 데이...