Search This Blog

November 19, 2010

Ordered Hashes in Ruby

Today, while playing a story in my web app development project, I felt the need to have an ordered hash in Ruby 1.8.7. Argh, this version of Ruby doesn't have ordered hash at all! Surprisingly enough, JRuby versions 1.3.1 or 1.5.1 preserves insertion order.

The way Ruby 1.8.7 hash behaves:

The way Ruby 1.9.1 hash behaves:

The way JRuby 1.3.1 hash behaves:

Coming back to our problem, how do I do have something like Ordered Hash data structure with Ruby 1.8.7? There are several libraries that either extend or replace Ruby's Hash. OrderedHash and RubyFacets being some of the famous ones. However, if you are developing a web application using Rails, then you have to search no where - just use Rails' ActiveSupport::OrderedHash. All you need to use it is
require 'active_support/ordered_hash' in your class/module

With Ruby 1.9, this wouldn't be a problem because Ruby 1.9 preserves the insertion order into the data structure. This only gives me foolish happiness for a second or two, after which my academic reasoning onsets bringing sinking unhappiness for the Ruby 1.9 preserving hash ordering by default. Should my prediction go right (or wish come true???) this will revert back to the way it was in Ruby 1.8.* and to solve this problem of having an ordered hash data structure, Ruby future version might have something like OrderedHash, the way Rails has one.

SIDE NOTE: A hash (table/map) is a data structure for storing items in key/value pairs using a hash function. Ideally, the hash function guarantees to map each key to a unique slot index. With this data structure, the average cost of lookup/insertion/deletion for an element remains constant irrespective of the number of elements that this data structure holds. Understandably for this reason this data structure is used in many softwares like databases, caches.


Recommended Books:

The Ruby Programming Language      Programming Ruby 1.9: The Pragmatic Programmers' Guide (Facets of Ruby)     The Well-Grounded Rubyist