2010-06-07 5 views
3

자바에서는 서버에 요청하는 라이브러리를 작성하기 위해 보통 연결 수를 제한하고 비동기 작업을 수행하기 위해 일종의 디스패처 (Twitter4J 라이브러리에있는 것과 다르지 않습니다. http://github.com/yusuke/twitter4j/blob/master/twitter4j-core/src/main/java/twitter4j/internal/async/DispatcherImpl.java)를 구현합니다.액터 "큐"?

아이디어는 N 개의 스레드가 생성된다는 것입니다. "작업"은 대기 상태이며 모든 스레드에 알리고 스레드 중 하나가 준비되면 대기열에서 항목을 팝하고 작업을 수행 한 다음 대기 상태로 돌아갑니다. 모든 스레드가 작업에 대해 작업하는 중이면 작업이 대기 상태가되고 다음 사용 가능한 스레드가 대기합니다.

최대 연결 수를 N으로 유지하고 최대 N 개의 작업을 동시에 실행할 수 있습니다.

나는 똑같은 것을 성취 할 배우들과 함께 어떤 종류의 시스템을 만들 수 있는지 궁금합니다. N 개의 액터를 가질 수있는 방법이 있습니까? 새 메시지가 준비되면 액터로 전달하여 처리하십시오. 모든 액터가 사용 중이면 메시지를 대기열에 넣으시겠습니까?

+1

Java 5가 표준 라이브러리에 있으므로 스레드 풀이 설명되어 있습니다. java.util.concurrent 패키지 (클래스 'ThreadPoolExecutor')를 참조하십시오. – Jesper

답변

4

Akka Framework.

액자 사서함을 관리하고 함께 작업 할 수있게 해주는 매우 구성 가능한 디스 패더 (이벤트 기반, 스레드 기반, 부하 분산, 작업 도용 등)가 많이 있습니다.이 docu을 살펴보십시오. 흥미로운 this blog post도 있습니다.

예. 디스패처 사용

val workStealingDispatcher = Dispatchers.newExecutorBasedEventDrivenWorkStealingDispatcher("pooled-dispatcher") 
    workStealingDispatcher 
    .withNewThreadPoolWithLinkedBlockingQueueWithUnboundedCapacity 
    .setCorePoolSize(16) 
    .buildThreadPool 

배우 : : 이제

class MyActor extends Actor { 

    messageDispatcher = workStealingDispatcher 

    def receive = { 
     case _ => 
    } 
    } 

를 시작하는 경우이 코드는 감독 배우들 사이에서로드 밸런싱을 충족 고정 스레드 풀을 기반으로 발송자 훔치는 새로운 일을 인스턴스화 액터의 인스턴스가 2 개 이상이라면 디스패처는 액터의 메일 박스 (큐) 사이의로드 밸런스를 조정합니다 (사서함에 너무 많은 메시지가있는 액터는 아무 것도하지 않는 액터에 일부를 "기부").

+0

나는 스케일러 메소드를 오버라이드하는 스칼라 액터들과 똑같이 할 수 있다고 생각합니다. – IttayD

1

일반적으로 액터가 스레드와 일대일로 일치하지 않으므로 배우 스케줄러에 대해 알아야합니다. 액터 뒤에있는 아이디어는 당신이 그 중 많은 것을 가질 수 있다는 것입니다. 그러나 실제 스레드 수는 합리적인 것으로 제한 될 것입니다. 그들은 장기간 실행되지 않아야하지만받는 메시지에 신속하게 응답해야합니다. 간단히 말해,이 코드의 아키텍처는 배우 시스템을 어떻게 디자인 할 것인가와는 완전히 다른 것처럼 보입니다.

여전히 각 작업자는 대기열 배우에게 다음 작업을 요청하는 메시지를 보낸 다음 반응하여 루프백 할 수 있습니다. 이 Queue 액터는 메시지 큐 또는 큐를 큐에서 수신합니다. 다음과 같이 설계 할 수있다 : 문제의이 종류를 해결하기 위해 설계되었으며, 당신이 찾고있는 정확하게이다

val q: Queue[AnyRef] = new Queue[AnyRef] 
loop { 
    react { 
    case Enqueue(d) => q enqueue d 
    case Dequeue(a) if q.nonEmpty => a ! (q dequeue) 
    } 
}