What is immutability and why should I worry about it?

GurdeepS picture GurdeepS · Mar 7, 2009 · Viewed 8.5k times · Source

I've read a couple of articles on immutability but still don't follow the concept very well.

I made a thread on here recently which mentioned immutability, but as this is a topic in itself, I am making a dedicated thread now.

I mentioned in the past thread that I thought immutability is the process of making an object read only and giving it low visibility. Another member said it didn't really have anything to do with that. This page (part of a series) uses an example of an immutable class/struct and it uses readonly and other concepts to lock it down.

What exactly is the definition of state in the case of this example? State is a concept which I haven't really grasped.

From a design guideline perspective, an immutable class must be one which does not accept user input and really would just return values?

My understanding is that any object which just returns information should be immutable and "locked down", right? So if I want to return the current time in a dedicated class with that one method, I should use a reference type as that will work a reference of the type and thus I benefit from immutability.

Answer

PCheese picture PCheese · Mar 8, 2009

What is Immutability?

  • Immutability is applied primarily to objects (strings, arrays, a custom Animal class)
  • Typically, if there is an immutable version of a class, a mutable version is also available. For instance, Objective-C and Cocoa define both an NSString class (immutable) and an NSMutableString class.
  • If an object is immutable, it can't be changed after it is created (basically read-only). You could think of it as "only the constructor can change the object".

This doesn't directly have anything to do with user input; not even your code can change the value of an immutable object. However, you can always create a new immutable object to replace it. Here's a pseudocode example; note that in many languages you can simply do myString = "hello"; instead of using a constructor as I did below, but I included it for clarity:

String myString = new ImmutableString("hello");
myString.appendString(" world"); // Can't do this
myString.setValue("hello world"); // Can't do this
myString = new ImmutableString("hello world"); // OK

You mention "an object that just returns information"; this doesn't automatically make it a good candidate for immutability. Immutable objects tend to always return the same value that they were constructed with, so I'm inclined to say the current time wouldn't be ideal since that changes often. However, you could have a MomentOfTime class that is created with a specific timestamp and always returns that one timestamp in the future.

Benefits of Immutabilty

  • If you pass an object to another function/method, you shouldn't have to worry about whether that object will have the same value after the function returns. For instance:

    String myString = "HeLLo WoRLd";
    String lowercasedString = lowercase(myString);
    print myString + " was converted to " + lowercasedString;
    

    What if the implementation of lowercase() changed myString as it was creating a lowercase version? The third line wouldn't give you the result you wanted. Of course, a good lowercase() function wouldn't do this, but you're guaranteed this fact if myString is immutable. As such, immutable objects can help enforce good object-oriented programming practices.

  • It's easier to make an immutable object thread-safe

  • It potentially simplifies the implementation of the class (nice if you're the one writing the class)

State

If you were to take all of an object's instance variables and write down their values on paper, that would be the state of that object at that given moment. The state of the program is the state of all its objects at a given moment. State changes rapidly over time; a program needs to change state in order to continue running.

Immutable objects, however, have fixed state over time. Once created, the state of an immutable object doesn't change although the state of the program as a whole might. This makes it easier to keep track of what is happening (and see other benefits above).