2012-01-24 4 views
17

Как я понимаю, актеры - это в основном легкие потоки, реализованные поверх потоков, запускающие много актеров в небольшом пуле общих потоков.scala актеры против потоков и блокировки IO

Учитывая это, использование блокирующих операций в акторе блокирует основной поток. Это не проблема корректности, потому что в библиотеке актера будут появляться новые потоки по мере необходимости (правильно?), Но потом вы получаете множество и много потоков, что отрицает преимущество использования актеров в первую очередь.

Учитывая, что, как работают актеры, когда вам нужно выполнять такие операции ввода-вывода? Существуют ли операции, которые «actor-block», приостанавливающие действие актера, позволяя потоку перейти к другим операциям (так как блокирующие операции приостанавливают поток, позволяя процессору перейти к другим операциям), или все, что написано на CPS, с цепью актеры? Или актеры просто не подходят для такого рода длительной операции?

История вопроса: У меня есть опыт написания многопоточного материала классическим способом, и хорошо понимаю, как работают циклы CPS/event, но не имеют абсолютно никакого опыта работы с актерами и просто хотят понять на высоком уровне, как они вписываются в , прежде чем погрузиться в код.

+1

Он должен включать в себя какое-то разграниченное продолжение, как в http://jim-mcbeath.blogspot.com/2010/09/scala-coroutines.html. Или, возможно, используя неблокирующий поток сообщений? (http://blog.typesafe.com/non-blocking-message-flow-with-akka-actors) – VonC

+0

См. мой ответ здесь http://stackoverflow.com/questions/1512066/is-there-any-non -blocking-ю-с открытым исходным кодом, реализация-для-scalas-актеров –

ответ

2

Это не проблема корректности, так как библиотека актер будет появляться больше потоков по мере необходимости (это правильно?)

Насколько я понимаю, что это не так. Актер заблокирован, и отправка другого сообщения приводит к тому, что сообщение сидит в почтовом ящике актеров до тех пор, пока этот актер не сможет отправить receive или react.

В Программе в Scala (1) он явно заявляет, что актеры не должны блокироваться. Если актеру нужно что-то делать, он должен передать работу второму актеру, чтобы главный актер мог освободиться и продолжить читать сообщения из своего почтового ящика. Как только работник завершит работу, он может подтвердить этот факт основному актеру, который может завершить все, что он должен делать.

Поскольку у рабочих тоже есть почтовые ящики, вы в конечном итоге столкнетесь с несколькими рабочими, работающими по работе. Если у вас недостаточно процессора, чтобы справиться с этим, их очереди будут становиться все больше и больше. В конце концов вы можете масштабировать, используя удаленных участников. Akka может быть более полезным в таких случаях.

(1) Глава 32,5 программирования в Scala (Одерски, второе издание, 2010 г.)

EDIT: Я нашел это:

Метод планировщика актора признака может быть переопределен возвращать ResizableThreadPoolScheduler, который изменяет размер пула потоков, чтобы избежать голода, вызванного актерами, которые вызывают произвольные методы блокировки.

Нашел на: http://www.scala-lang.org/api/current/scala/actors/Actor.html

Итак, это означает, что в зависимости от планировщика осущ вы установили, возможно, бассейн используется для запуска актеров будут увеличены. Я ошибся, когда сказал, что вы ошибаетесь :-) Остальная часть ответа по-прежнему сохраняется.

1

Как все работает в erlang, так это то, что вся операция блокировки должна быть отправлена ​​посылкой сообщения, потому что когда ваш актер заблокирован в ожидании сообщения, он передает поток другому игроку.

Так что если вы хотите сделать некоторые операции блокировки, такие как чтение из файла, вы должны сделать актера FileReader, который использует Non-bloking api для чтения и записи из файла. И попросите своего другого актера использовать этого актера (отправить и получить сообщение) в качестве api для чтения и записи в файл.

Смежные вопросы