4 ms·
What I found interesting (or very, very boring, depending on how you think about it) about this when I first saw it is that this ability is just due to the natu
by lostcolony 10y ago
What I found interesting (or very, very boring, depending on how you think about it) about this when I first saw it is that this ability is just due to the nature of how receive works. That is, you can receive any kind of message, at any time. Want to listen to a different set of messages? Just call a different receive clause, be that in a different function, or inline.
I remember having a coworker who was in love with Akka. He was trying to sell everyone on it, despite my team's having a strong Erlang presence. He showed us Akka's "become", talking about how powerful that could be, and how Erlang didn't have anything comparable. He didn't seem to realize that Akka's needing a special keyword for it was actually a limitation rather than a feature, that Erlang didn't have a special keyword to allow you to do it because it didn't -need- a special keyword to allow you to do it. That's not a dig at Akka, or Scala (it's an impressive language in its own right), but rather to point out how sometimes we miss the complex capabilities a simple set of abstractions can give us.
- qaq 10y agoIs he aware of how Akka came into existence :)?
- _asummers 10y agoRe: Akka, to paraphrase James Gosling's comments on Java "We brought a bunch of Java programmers halfway to Erlang".
- qaq 10y agohalfway is very optimistic interpretation :)
- phyrex 10y agoFYI that wasn't Gosling, that was Guy Steele: http://people.csail.mit.edu/gregs/ll1-discuss-archive-html/msg04045.html http://people.csail.mit.edu/gregs/ll1-discuss-archive-html/m...
- _asummers 10y agoMy mistake! And in retrospect, Guy Steele saying that makes way more sense.
- lmm 10y agoYou don't need to use "become" in Akka - you can just call a function blindly if you want. It's useful to have a distinct concept of "become", because it's useful to not have arbitrary invisible behaviour changes everywhere, but rather demarcate which parts of the system do what. (I mean, just imagine trying to debug a system based on this universal server).
- yetihehe 10y agoNot a problem, in stacktraces you can see where it was called and which line causes errors. Also you can dynamically trace this and even trace only those servers which become what you want. I've debugged systems which behave similarly, it's easy after you learn you can write "debugging servers" which are as simple as this "become server".
- lostcolony 10y agoHow does that work? I've never seen an example, and I don't see how you could do it cleanly without growing the stack, given the JVM's constraints. Also to add onto yetihehe's comment, it's -really freaking easy- to debug such a server as Joe illustrates, or anything else that behaves in such a way (changing behavior by calling another function, to eventually wind up in a different receive statement), in Erlang. It's effectively an FSM determining what kind of messages you handle, the stack traces are clean (TCO means any time you get an exception, it's only in the current 'state'); the only complexities are the fact you're building an FSM, i.e., making sure your transitions are right, and what to do about out of order messages (i.e., a message that doesn't match the current state). There's nothing specific about the Erlang code that makes it harder to debug than the Akka code; in fact, just the fact it's pure Erlang makes it easier; your stack traces are going to be just your own code, no libraries muddying them up. As for demarcation...it's not really any different. That is, Scala's def func:Receive = { //cases } def receive = { case "foo" => become(func) } is equivalent to Erlang's func() -> receive %cases end. receive "foo" -> func() end. But you'll note that in Joe's example he even uses the atom 'become' to indicate the transition is happening, i.e., receive {become, F} => F() end). It's totally equivalent. I'm not saying Scala is less clean, or whathaveyou, just that Akka felt they had to create a new keyword, for some reason, rather than leave it up to the user to implement. Exactly why, or whether it's equivalent to calling a function, I don't know (having never seen an example of the latter, nor commentary on its characteristics re: call stack); my point was simply that it's a natural extension of the language fundamentals in Erlang, but Akka felt the need to create a new keyword just for it, and that people often miss that needed complexity can arise out of a solid set of fundamentals.