

(For what its worth, you can implement message passing using mutable messages, its just that no one ever wants to because a thread can't do anything to the message without locking it - which we already know is full of problems. And its exactly because threads can send and receive messages across the process boundary that message passing scales as well as it does, because its not bound to a single machine, you can have your app running across as many machines as needed. Is there really a difference between passing a message to a thread in the same process vs passing a message to thread listening on some IP address? Not really. You can't obtain a lock on an object across processes.īut think about the message passing model above: threads are passing messages two and from one another. Traditional locking doesn't scale well because, in order to lock an object, you need to have a reference to its pointer - the locked object needs to be in the same memory as the object doing the locking. So the important part of Joel's comment: "Without understanding functional programming, you can't invent MapReduce, the algorithm that makes Google so massively scalable." Its also possible for a thread to pass itself as a message, so that Thread A sends itself to Thread B, then thread B sends a message back to Thread A via the pointer it received.īelieve me, the strategy above makes concurrent programming 1000x easier than locks on mutable state. So if thread A has a pointer to thread B, it can pass a message - the updated data structure - to thread B, where thread B merges its copy with the data structure with the copy in the message it received. Instead of having two threads sharing state with one another, we think of threads as being a kind of mailbox which can send and receive messages. The trick is to re-think our concurrency model.

There are times when we need changes in one thread to be visible to another - so how do we do that with immutable objects? Since we don't have race-conditions, we don't have any need for locks, so we also eliminate a whole class of errors related to deadlocking.īecause immutable objects are intrinsically thread-safe, they're said to make concurrency "trivial". Since the tree is immutable, its not possible for one thread to put the object in an invalid state under another thread's nose - so we eliminate a whole class of multithreading errors related to race conditions. Think about it: if you have an immutable tree or any other data structure, then you can two threads inserting, removing, and lookup up items in the tree without needing to take a lock. The only difference is that inserting returns a new version of your data structure without modifying the original one. In most cases, the immutable version of a data structure has the same computational complexity for insert/lookup/delete as its mutable counterparts. See here for an implementation of an immutable treap. In fact, its extremely easy to write immutable versions of many common data structures - like immutable Avl Trees, red-black trees, many kinds of heaps, etc. You'll be surprised how far you can carry this style of programming. If parts of your object graph haven't changed, can reuse it in your new object (copy the pointer, don't new up a new instance of any objects in that part of the graph). The trick is realizing that you don't have to copy your entire object graph, only the parts which have changed. "But Juliet!? How can this possibly be efficient with all this copying?" So all the initialization take place in the constructor, and we can't modify the object ever again - we create new instances with our modifications passed into the constructor. returns a new customer with the given name You "modify" things by creating a new instance of your object with modified state. "But Juliet! How can write a useful program if it can't modify anything" When Joel says functional programs have no side-effects, there's a lot of hand-waving involved since its perfectly easy to write functional programs which do modify variables - but largely, when people talk about functional programming, they mean programs which don't hold any modifiable state. Variables "vary", hence the name.įunctional programming is a style of designing programs to eliminate variables - everything is a constant or readonly. Most people think of programming as creating variables, assigning them values, adding things to lists, etc.
