In the book Java Concurrency In Practice it explains the advantages of \"effectively immutable\" objects versus mutable objects concurrency-wise. But it does not explain what a
Suppose one has an immutable class Foo
with five properties, named Alpha
, Beta
, etc., and one wishes to provide WithAlpha
, WithBeta
, etc. methods which will return an instance which is identical to the original except with the particular property changed. If the class is truly and deeply immutable, the methods have to take the form:
Foo WithAlpha(string newAlpha) { return new Foo(newAlpha, Beta, Gamma, Delta, Epsilon); } Foo WithBeta(string newBeta) { return new Foo(Alpha, NewBeta, Gamma, Delta, Epsilon); }
Ick. A massive violation of "Don't Repeat Yourself" (DRY) principles. Further, adding a new property to the class would require adding it to every single one of those methods.
On the other hand, if each Foo
held an internal FooGuts
which included a copy constructor, one could instead do something like:
Foo WithAlpha(string newAlpha) { FooGuts newGuts = new FooGuts(Guts); // Guts is a private or protected field newGuts.Alpha = newAlpha; return new Foo(newGuts); // Private or protected constructor }
The number of lines of code for each method has increased, but the methods no longer need to make any reference to any properties they aren't "interested" in. Note that while a Foo
might not be immutable if its constructor were called with a FooGuts
to which any outside reference existed, its constructor is only accessible to code which is trusted not to maintain any such reference after construction.