Using Hashes in Javascript
You may have noticed that the JavaScript literature rarely mentions hashes. Fortunately, they're available, even though not directly supported. They can be implemented by defining hashes as objects and keys as properties:
$o_myhash = new Object( ); $o_myhash["a"] = "apple"; $o_myhash["b"] = "banana";
Initializing a hash of any size, however, is messy, as is evident by extrapolating the above example. This paper presents a constructor that facilitates initialization. Once a hash is built, use
for ($key in $o_myhash) { some code }
to iterate through it. Hash inversion is discussed near the bottom of this page.
Constructor
The specialized Hash constructor enables single-step creation and initialization of an entire hash. Hash can be used with any of three calling sequences, as defined near the top of the code below.
/* Copyright 1999 David S. Jackson. All rights reserved.
** You may use the code as long as this header remains intact.
**
** Calling sequences for the Hash constructor:
** 1. $o_myhash = new Hash(
** "a" , "apple",
** "b", "banana"
** ); // example
** 2. $o_myhash = new Hash($a_pairs); // $a_pairs is an array
** containing key-value pairs (key0, val0, key1, val1, etc.)
**
** 3. $o_myhash = new Hash($a_keys, $a_values);
********************************************************************
function Hash( ... see options above ...)
{
// size of variable-length sequence
var $len = Hash.arguments.length;
// length of first param: array or just a variable?
var $length0 = Hash.arguments[0].length;
if ($len == 1) {
//======================================================
// input assumed to be the pairs array
//=====================================================
if ($length0 % 2 == 1) {
alert ("Error: pairs array has an extra key.");
return;
}
for ($i = 0; $i < $length0; $i += 2)
eval ("this['" + Hash.arguments[0][$i ] + "'] = '"
+ Hash.arguments[0][$i+1] + "';");
return;
}
if (($len == 2) && ($length0 > 1)) {
//======================================================
// input is keys, values arrays
//======================================================
if ($length0 != Hash.arguments[1].length) {
alert ("Error: keys and values arrays are different length.");
return;
}
for ($i = 0; $i < $length0; i++)
eval ("this['" + Hash.arguments[0][$i] + "'] = '"
+ Hash.arguments[1][$i] + "';");
return;
}
//======================================================
// input is a sequence of keys and values
//======================================================
// check for balanced number of key-value pairs
if ($len % 2 == 1) {
alert ("Error: extra key in Hash() calling sequence.");
return;
}
for ($i = 0; $i < $len; $i += 2)
// swap $i and $i+1 to invert the hash
eval ("this['" + Hash.arguments[$i ] + "'] = '"
+ Hash.arguments[$i+1] + "';");
}
Inverting a Hash
It's fairly easy to invert a hash (swapping keys and values; all values must be unique, else hash entries will be undefined). Use a slightly different approach for each constructor calling sequence:
- For Hash($a_pairs), use $a_pairs.reverse( ) before calling Hash.
- Hash($a_values, $a_keys) inverts the two-array version.
- For the other option, it may be simplest to copy and rename the Hash constructor, swapping the two indices in the eval statement at the bottom of the code.