Friday, January 14, 2011

Enum subsets in C#

After a few years of working with Haskell I've become nearly obsessed with expressing constraints in the type system. Although the C# type system isn't as expressive as Haskell's, preconditions, postconditions, ranges, complexity, and other things can be expressed. If the type is expressive enough then you don't even have to do any validation or checking when working with it because the compiler already guaranteed that the data is valid. One of the problems with C# enums is that they aren't real objects so they can't subclass; they're just pretty wrappers around primitives like ints or bytes. This means that if you only allow certain values of an enum then you have to manually check at runtime:

public void DeclareDayIsSpecial(DayOfWeek day)
  if (day == DayOfWeek.Sunday || day == DayOfWeek.Saturday)
    throw new ArgumentException("When declaring that a day is special, the day must be a weekday.", "day");
  Console.WriteLine("{0} is special.", day);

Even though you can't define an enum as a subclass of another and allow only that subclass, you can define an enum as subset of another.

public enum Weekday
   Monday = DayOfWeek.Monday,
   Tuesday = DayOfWeek.Tuesday,
   Wednesday = DayOfWeek.Wednesday,
   Thursday = DayOfWeek.Thursday,
   Friday = DayOfWeek.Friday,

Once you have this you can constrain your methods to just the valid subset of values.

public void DeclareDayIsSpecial(Weekday weekday)
  Console.WriteLine("{0} is special.", weekday);

The compiler won't allow you to use an invalid value so you have compile time documentation and feedback and can remove the runtime checks. This can be useful if you use enums in a scenario where only some values are valid. And since enums are wrappers around primitive types, you can safely cast from the subset (Weekday) to the superset (DayOfWeek).


  1. What about casting from the superset (DayOfWeek) to the subset (Weekday)? Is there a fast, non-boilerplatish way to do the cast and throw an exception if the value isn't part of the subset?

  2. I always enjoy reading quality articles by an individual who is obviously knowledgeable on their chosen subject. Ill be watching this post with much interest. Keep up the great work, I will be back

    Data Science Training in Chennai
    Data Science course in anna nagar
    Data Science course in chennai
    Data science course in Bangalore
    Data Science course in marathahalli
    Data science course in bangalore