2016-10-29 3 views
1

나는 10000 명의 배우를 만들고 각각에게 메시지를 보내지 만, akka 시스템이 모든 작업을 완료 할 수없는 것으로 보입니다. 스레드 상태를 확인할 때 그들은 모두 TIMED_WATIING입니다.액터가 10000 개를 만들었지 만 액터가 왜 모든 작업을 완료 할 수 없습니까?

내 코드 :

scala.concurrent.blocking { 
    Thread.sleep(2000) 
} 

scala.concurrent.blocking가 차단 관리해야하는 계산을 표시 : (당신이 기본 스레드 풀을 사용하는 경우)

class Reciver extends Actor { 
    val log = Logging(context.system, this) 
    var num = 0 

    def receive = { 
    case a: Int => log.info(s"[${self.path}] receive $a, num is $num") 
     Thread.sleep(2000) 
     log.info(s"[${self.path}] processing $a, num is $num") 
     num = a 
    } 
} 

object ActorSyncOrAsync extends App { 
    val system = ActorSystem("mysys") 

    for (i <- 0 to 10000) { 
    val actor = system.actorOf(Props[Reciver]) 
    actor ! i 
    } 
    println("main thread send request complete") 
} 

답변

4

당신은 그것을 둘러싸고 Thread.sleep를 제거하거나한다 이는 계산이 CPU 리소스를 사용하지 않고 일부 결과 또는 시간 초과를 기다리고 있음을 풀에 알리는 것을 의미합니다. 그러나 be careful with this해야합니다. 따라서 기본적으로이 조언은 디버그 목적으로 또는 Thread.sleep (심지어는 blocking으로 둘러싸인)을 모방하기 위해 Thread.sleep을 프로덕션 코드에서 사용해야하는 경우 작동합니다.

설명 : 일부 고정 수영장이 (가 Thread.sleep에 의해 차단 된 스레드에서 작업을 도둑질하지 않는 한 포크 - 조인 포함)를 사용

- 만 POOL_SIZE 스레드 (이 코어의 수에 동일이 기본적으로 시스템에서)이 계산에 사용됩니다. 다른 모든 것은 대기 행렬에 놓이게 될 것입니다.

그래서 4 코어, 작업 당 2 초, 10000 개의 작업 - 2 * 10000/4 = 5000 초 걸릴 것입니다.

귀하의 배우 내에서 (Thread.sleep 포함)을 차단하지 않으려면 으로 문의하십시오. Blocking needs careful management. 어떤 동작을 지연해야한다면 스케쥴러 (@Lukasz 언급 한대로)를 사용하는 것이 더 좋습니다 : http://doc.akka.io/docs/akka/2.4.4/scala/scheduler.html

+0

아마도 그는 수면 후 메시지 처리 부분을 수행하고 수면을 완전히 제거하기 위해 스케줄러를 사용해야합니다. –

+0

@ 루카스 나는 Thread.sleep이 목적을 디버깅하기위한 것이라고 생각하지만이 정보를 대답에 추가 할 것이다. 감사! – dk14

관련 문제