A common pain point in .NET programming is the amount of boilerplate code necessary to implement immutable objects. Unlike a normal class, and immutable class requires that each property have an explicitly defined backing store. And of course a constructor is needed to tie everything together.
Under a new draft specification, C# and VB will be adding what they are calling a “record class”. This is essentially an immutable class defined solely by its constructor. Here is an example from the specification:
public record class Cartesian(double x: X, double y: Y);
In addition to the constructor, the compiler will automatically create:
- A read-only property for each parameter
- An Equals function
- A GetHashCode override
- A ToString Override
- An “is” Operator, known as “Matches” in VB
The “is/Matches” operator is used in pattern matching, which we will cover in tomorrow’s article. Aside from that, record classes are a lot like C# anonymous types. (VB anonymous types differ in that they are mutable by default.) Microsoft is looking into ways to reconcile the two concepts, especially given the current limitation about not exposing anonymous types beyond their current assembly.
A common feature of immutable types is the ability to create copies of the object with one or more fields updated. Though not in the specification yet, here is one option they are considering for C#.
var x1 = new MyRecord(1, 2, 3);
var x2 = x1 with B: 16;
Console.WriteLine(x2) // prints something like "A = 1, B = 16, C = 3"
Extending Record Classes
In the Cartesian example class, you may have noticed that it ended with a semi-colon. This is to indicate that the class has no body other than what the compiler provides.
Instead of the semi-colon you can provide a set braces like you would for a normal class. You would still get the same compiler-generated code, but have the ability to add additional properties and methods as you see fit.
Other Limitations
For the time being only record classes are supported. In theory, record structs could be added using the same basic syntax and concepts.
Library Concerns
A serious limitation of immutable types in .NET is the lack of library support. Imagine that you are a middle tier developer. Your normal day-to-day tasks probably involve asking an ORM for some objects out of the database, which you then serialize as SOAP-XML or JSON for a one-way or round-trip to the client.
Currently most ORMs and serializers don’t have support for immutable types. Instead, they assume there will be a parameterless constructor and mutable properties. If this issue isn’t resolved in the more popular frameworks, record classes will be of little use in most projects.
For more information, see the draft specification Pattern Matching for C#. A prototype should be available in a few weeks.
Correction: This report erroneously stated that this feature would be part of C# 6 and VB 12.