zlacker

[parent] [thread] 10 comments
1. koakum+(OP)[view] [source] 2026-02-02 07:02:59
So you're just using actors to limit concurrency? Why not use a mutex?
replies(4): >>raphin+w2 >>rurban+va >>crusty+Wf >>whizzt+Np
2. raphin+w2[view] [source] 2026-02-02 07:29:56
>>koakum+(OP)
This might be a question of personal preference. At the design stage I already find it more approachable to think in separated responsibilities, and it naturally translates to actors. Thinking about the app, it's much reasier for me to thin "send the message to the actor" than call that function that uses the necessary mutex. With mutexes, I think the separation of concerns is not as strong, and you might end up with a function taking multiples mutexes that might interfere. With the actor model, I feel there is less risk (though I'm sure this would be questioned by seasoned mutex users).
3. rurban+va[view] [source] 2026-02-02 09:01:52
>>koakum+(OP)
Because actors were invented to overcome deadlocks caused by mutexes. See page 137. With mutexes you can forget concurrency safety.
replies(1): >>ahoka+Ny
4. crusty+Wf[view] [source] 2026-02-02 09:58:01
>>koakum+(OP)
You are using mutexes, they are on the Actor message queues, amongst other places. "Just use mutexes" suggests a lack of experience of using them, they are very difficult to get both correct and scalable. By keeping them inside the Actor system, a lot of complexity is removed from the layers above. Actors are not always the right choice, but when they are they are a very useful and simplifying abstraction.

Horses for courses, as they say.

replies(2): >>b33j0r+GL >>koakum+SU6
5. whizzt+Np[view] [source] 2026-02-02 11:37:55
>>koakum+(OP)
In this simple case they're more or less equivalent if the only task is limiting concurrency, but in general usage of mutexes multiplies and soon enough someone else has created a deadlock situation.

Extending it however reveals some benefits, locking is often for stopping whilst waiting for something enqueued can be parallell with waiting for something else that is enqueued.

I think it very much comes down to history and philosophy, actors are philosophically cleaner (and have gained popularity with success stories) but back in the 90s when computers were physically mostly single-threaded and memory scarce, the mutex looked like a "cheap good choice" for "all" multithreading issues since it could be a simple lock word whilst actors would need mailbox buffering (allocations... brr),etc that felt "bloated" (in the end, it turned out that separate heavyweight OS supported threads was often the bottleneck once thread and core counts got larger).

Mutexes are quite often still the base primitive at the bottom of lower level implementations if compare-and-swap isn't enough, whilst actors generally are a higher level abstraction (better suited to "general" programming).

replies(1): >>zozbot+Jw
◧◩
6. zozbot+Jw[view] [source] [discussion] 2026-02-02 12:36:24
>>whizzt+Np
Atomic operations, memory barriers, condition variables, thread/"virtual processor" scheduling are philosophically cleaner since they're what the specified hardware/OS concurrency model actually provides, and can implement all of locks, mutexes, structured concurrency, arbitrary queues, actors etc. etc.
replies(1): >>whizzt+Wjc
◧◩
7. ahoka+Ny[view] [source] [discussion] 2026-02-02 12:48:56
>>rurban+va
I’m pretty sure it’s possible to deadlock an actor system.
replies(1): >>rurban+Jo1
◧◩
8. b33j0r+GL[view] [source] [discussion] 2026-02-02 14:08:11
>>crusty+Wf
Lock-free queues and 16-core processors exist though. I use actors for the abstraction primarily anyway.
◧◩◪
9. rurban+Jo1[view] [source] [discussion] 2026-02-02 17:28:11
>>ahoka+Ny
A bad one, yes. But it was esp. invented to prevent the mutual exclusion problem. And good actor systems do so.
◧◩
10. koakum+SU6[view] [source] [discussion] 2026-02-04 00:53:32
>>crusty+Wf
Can you share some insights why mutexes are difficult to get correct and scalable?
◧◩◪
11. whizzt+Wjc[view] [source] [discussion] 2026-02-05 15:19:14
>>zozbot+Jw
I was implicitly including all those with mutexes in the last sentence, it might be easier to reason about each in isolation because you're an experienced programmer that can/want to reason about the details.

In practice you want to keep the sharp knives away from junior programmers in larger contexts, handling a few ones in a limited scope is ok but when you start to reason about larger systems, actors in concurrent contexts can be explained even to junior programmers in terms of conveyor belts of messages or a similar analogy.

I don't know if you heard the story of how C++ was used and a large part of the collapse of that project was due to C++, OO and/or threading issues and how Erlang was then used in a crash project to successfully write a replacement on the same HW.

Some people claim that functional programming and/or actor systems are inherently superior, I don't really agree on that assessment, it's more that the actor patterns were easily handled in a distributed system and when used by less seasoned programmers it was possible for them to create their parts in mostly "single-threaded" contexts + message passing without causing trouble by using lower level concurrency primitives.

Really, imagine 500+ mid-junior programmers banging away concurrent code on a larger project that needs to be shipped soon.

This is what I mean by philosophically cleaner.

[go to top]