{"id":1324,"date":"2010-07-24T00:58:30","date_gmt":"2010-07-23T14:58:30","guid":{"rendered":"http:\/\/www.somethinkodd.com\/oddthinking\/?p=1324"},"modified":"2010-07-27T17:17:30","modified_gmt":"2010-07-27T07:17:30","slug":"enumerating-features-of-enumerated-types","status":"publish","type":"post","link":"https:\/\/www.somethinkodd.com\/oddthinking\/2010\/07\/24\/enumerating-features-of-enumerated-types\/","title":{"rendered":"Enumerating Features of Enumerated Types"},"content":{"rendered":"<p>If you aren&#8217;t into programming language design, you can skip this.<\/p>\n<p>For the rest of us, I want to talk enumerated types. It is a discussion I have with myself frequently.<\/p>\n<h3>Simple Modelling Challenge<\/h3>\n<p>Consider how you would model this decision at your local chip shop, in your favourite programming language.<\/p>\n<p>Milkshakes can be chocolate, vanilla or strawberry &#8211; that&#8217;s all they sell. They can be small, medium or large.<\/p>\n<h3>How to Assess The Result?<\/h3>\n<p>Here are some questions for you:<\/p>\n<p>Does your language ensure that the milkshake could only be those flavours. Will it permit someone to say a milkshake is blueberry flavoured?<\/p>\n<p>Does your language support the concept that large is greater than medium? (Conversely, can you say that Vanilla and Strawberry do not support the greater-than relationship?)<\/p>\n<p>Can you loop over the flavours?<\/p>\n<p>Do you have to specify an internal integer representation? Or will your language assign values for you?<\/p>\n<p>Can you learn that internal integer representation for use as a key? What about for use as serialisation (which requires you to be able to go the other way, too, from integer to enumerated value)?<\/p>\n<p>Can you override the internal integer representation? e.g. to map large to its size in millilitres.<\/p>\n<div class=\"aside\">If you want to argue that I just overstepped the meaning of an enumerated type, I will agree with you. However, it often comes up during development.<\/div>\n<p>Is there a text representation available so you can easily print &#8220;Strawberry&#8221; rather than 2?<\/p>\n<h3>Some I Prepared Earlier<\/h3>\n<p>Here are what I believe the answers are for several classic languages &#8211; some have more than one way to implement this. [Source: Memory and  <a href=\"http:\/\/en.wikipedia.org\/wiki\/Enumerated_type\" title=\"Wikipedia definition of Enumerated_type\" class=\"wikipedia\">Wikipedia<\/a>]<\/p>\n<table class=\"simple\">\n<tr>\n<th>Language (Technique)<\/th>\n<th>Type-Checked<\/th>\n<th>Order Available?<\/th>\n<th>Order Mandatory?<\/th>\n<th>Iterable?<\/th>\n<th>Visible integer representation?<\/th>\n<th>Serialisable?<\/th>\n<th>Has Auto-Inc value<\/th>\n<th>Has Overridable value<\/th>\n<th>Has Text Representation<\/th>\n<\/tr>\n<tr>\n<th>Pascal<\/th>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<sup>3<\/sup><\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<td>FALSE<\/td>\n<\/tr>\n<tr>\n<th>C (Enum)<\/th>\n<td>FALSE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<sup>6<\/sup><\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<\/tr>\n<tr>\n<th>C++ (Enum)<\/th>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<sup>6<\/sup><\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<\/tr>\n<tr>\n<th>C\/C++ (Const)<\/th>\n<td>FALSE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<\/tr>\n<tr>\n<th>Java<\/th>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<\/tr>\n<tr>\n<th>Python (Dict)<\/th>\n<td>Manual<sup>2<\/sup><\/td>\n<td>TRUE<sup>5<\/sup><\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<sup>4<\/sup><\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<\/tr>\n<tr>\n<th>Python (Set)<\/th>\n<td>Manual<sup>2<\/sup><\/td>\n<td>FALSE<\/td>\n<td>N\/A<\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<td>FALSE<sup>4<\/sup><\/td>\n<td>N\/A<\/td>\n<td>FALSE<\/td>\n<td>TRUE<\/td>\n<\/tr>\n<tr>\n<th>Python (Enum Class<sup>1<\/sup>)<\/th>\n<td>Manual<sup>2<\/sup><\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE?<\/td>\n<td>TRUE<\/td>\n<td>FALSE<sup>4<\/sup><\/td>\n<td>FALSE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<\/tr>\n<tr>\n<th>SQL<\/th>\n<td>TRUE?<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>FALSE?<\/td>\n<td>TRUE?<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>FALSE<\/td>\n<td>TRUE?<\/td>\n<\/tr>\n<tr>\n<th>Ada<\/th>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<\/tr>\n<tr>\n<th>C#<\/th>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<td>TRUE<\/td>\n<\/tr>\n<\/table>\n<p><sup>1<\/sup> I frequently use this <a href=\"http:\/\/www.radlogic.com\/releases\/enum_meta.py\">Enum class<\/a> I found on the web. I frequently regret it, because I keep forgetting it doesn&#8217;t offer everything Ada did (in 1983!).<\/p>\n<p><sup>2<\/sup> Python is dynamically typed. You can write, for example, <code>assert flavour in milkshake_flavours<\/code>, but it won&#8217;t be checked for you, so you need to do it explicitly.<\/p>\n<p><sup>3<\/sup> Standard Pascal doesn&#8217;t support it but several implementations, and derived languages, do.<\/p>\n<p><sup>4<\/sup> It is possible to create back-mappings, but they are look-ups, not trivial type-coercions.<\/p>\n<p><sup>5<\/sup> By comparing the values from the dictionary yourself:  <code>CUP_SIZE['large'] > CUP_SIZE['small']<\/code> Without manual sorting, iteration will not be in this order.<\/p>\n<p><sup>6<\/sup> De-serialising a value known to be good can be done for free &#8211; a coercion in C, or a cast in C++. Detecting whether such a value is good is hard.<\/p>\n<h3>Conclusion<\/h3>\n<p>Sometimes, I miss Ada.<\/p>\n<p>[<strong>Updated to include C#, separate C++ enums and indicate Java&#8217;s overridable nature, iterability and text representation, according to help from commenters. Thank you.]<\/strong><\/p>\n","protected":false},"excerpt":{"rendered":"<p>In which Enumerated Types are compared by programming language<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_s2mail":"","footnotes":""},"categories":[1],"tags":[],"class_list":["post-1324","post","type-post","status-publish","format-standard","hentry","category-uncategorized"],"_links":{"self":[{"href":"https:\/\/www.somethinkodd.com\/oddthinking\/wp-json\/wp\/v2\/posts\/1324","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.somethinkodd.com\/oddthinking\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.somethinkodd.com\/oddthinking\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.somethinkodd.com\/oddthinking\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.somethinkodd.com\/oddthinking\/wp-json\/wp\/v2\/comments?post=1324"}],"version-history":[{"count":20,"href":"https:\/\/www.somethinkodd.com\/oddthinking\/wp-json\/wp\/v2\/posts\/1324\/revisions"}],"predecessor-version":[{"id":1349,"href":"https:\/\/www.somethinkodd.com\/oddthinking\/wp-json\/wp\/v2\/posts\/1324\/revisions\/1349"}],"wp:attachment":[{"href":"https:\/\/www.somethinkodd.com\/oddthinking\/wp-json\/wp\/v2\/media?parent=1324"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.somethinkodd.com\/oddthinking\/wp-json\/wp\/v2\/categories?post=1324"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.somethinkodd.com\/oddthinking\/wp-json\/wp\/v2\/tags?post=1324"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}