Given an execution context and a thread pool, how are akka/scala actors scheduled/implemented on that?
问题:
回答1:
I was confused with this topic for a long time. I assumed that there is some relation between threads and actors. For each actor there is a thread that hosts it, so I was thinking. Probably there are several actors for each thread that works in cooperative multitasking mode.
Documentation is focused on usage and cover internal architecture lightly. You just should extend Actor
class and you would get working actor. So I tried to guess how can this be done. And imagined that each Actor
has life-cycle. Something like wait asynchronously for message queue. Then process message. Go to start.
That was totally false assumption. Although the documentation says "actor life-cycle" it does not mean Actor
life-cycle. Actor mentioned is a conception rather than actual object implementing the Actor
class. The object resides passive in the java heap.
To breath life into the conception coordinated work involving bunch of real workers is needed. And the heart of it is dispatcher. It holds all actors, threads and messages. And when resources become available and there are message available for processing the dispatcher activates. It takes appropriate Actor
object, wraps its receive method in runnable and pass it to a spare thread. So there is no life-cycle for the object only occasional method calls from the actor system.
When you think of it, it makes much more sense than scheme I assumed early. But it was hard for me to deduce it from available documentation. It was written by seasoned concurrency programmers. The distinguish holding the actor class from actor conception behind it. They know that dispatcher for an actor system is like task scheduler for an OS. So they quickly get to the point and describes various flavours and realization of the conception assumed be familiar to everyone.
But that is not so easy for a newbie. He has no acquaintance of the dispatcher pattern in actor systems context. I tried to google "dispatcher pattern" and it showed only non-relevant to an actor system definitions.
I've found easily double dispatch, multi-dispatch and other OOP topics. I've found something similar to akka's routers message dispatcher. There is probably decent description for actor message dispatchers but it not so easy to find.
I hope I've cleared the misunderstanding.
回答2:
On 'I was looking into something more like say you are given a thread pool of 10 threads and 50 actors spun off of it, how are so many actors handled by a batch of 10 threads?'
The exact behavior depends on the dispatcher and configuration. However, most dispatchers do basically something like this:
- Select an actor which has a non-empty mailbox
- That 'actor' is then dispatched to run on the executor
- Where messages are dequed and processed.
- When possible, a few messages are dequed and processed one after another
- After processing some messages (or none left), another actor is picked, to prevent starvation. (throughput parameter)
- Rise and repeat
回答3:
You can find relevant information in the akka documentation which is pretty complete as far as thing goes.
Essentially you can select/define dispatchers and assign actors to them through configuration (via files or code).
Each dispatcher implementation is then based on some sort of executor.