[erlang-questions] Why single-assignment with non-shared state?

2007/10/20, Matej Kosik <kosik@REDACTED>: > > Doesn't shadowing of meanings of variables in Erlang similarly > complicate reasoning? (in one position some variable has some > meaning and elsewhere in the term suddenly has different meaning). Well, it could, but in most cases where it would be confusing, the compiler will give you a warning. Personally, I try to use some naming convention for variables to minimize the risk of confusion. > Non-functional features of Erlang are present in its fundamental constructs: > - - send > - - receive > - - spawn > These cannot be modelled in (purely) functional languages, can they? How? Almost by definition, the answer is "no", I think? (: (I guess I should let the real language experts answer this, but it's Saturday, and I don't have anything better to do right now. I trust I'll get my fingers slapped if I write something stupid). At least it's difficult. Haskell uses 'monads', to clearly mark where the code has side-effects. This allows the compiler to trust that all code outside of the monad is pure. Other languages can use the fact that these operations are contained within the runtime, and can optimize them. Felix* does this, for example; I don't know about Concurrent ML. I believe that when Felix participated in the Language Shootout, its compiler reduced the concurrency benchmark down to a function that did nothing**. This doesn't mean that Felix models "fibres" as being pure, but as long as the effect of the impurity is understood, a smart compiler can sometimes eliminate it, or at least simplify it significantly. I guess this is sort of a grey area. (: It is partly connected to the fact that most of the surroundings are pure, and very well understood. Erlang can, for example, decide to pass a pointer rather than copy a message, since there are no user-level operations that can mess with the low-level representation of the message. There was once a paper suggesting that a gen_server:call() could be reduced to a function call, under certain circumstances (http://www.erlang.se/workshop/2002/Stenman.pdf), but it suggested dynamic checking to ensure that the conditions were met, since it would be difficult to do statically in Erlang. (OHaskell not only performs this check statically, it enforces it: http://www.cs.chalmers.se/~nordland/ohaskell/) Erlang's approach is fairly pragmatic. It has basically tried to make sure that all non-pure operations can be modeled using spawn, send and receive, but the only parts of an erlang program that the compiler can trust to be free from side-effects are clause heads, the left hand side of an expression (pattern matching), and guard expressions. Every (non-guard) function call can potentially result in a side-effect. Some BIFs are also known to be pure and can be optimized by the compiler. * http://www.felix-lang.org - a OCaml/C++ hybrid of sorts ** This Felix entry was disqualified, which caused some debate. Google will tell you more. BR, Ulf W