17

I want to use a Structure like HashTable. Is there similar structure in Wolfram Mathematica?

JayC
  • 7,053
  • 2
  • 25
  • 41
Yongwei Xing
  • 12,983
  • 24
  • 70
  • 90

5 Answers5

22

Update: Mathematica version 10 introduced the Association data structure (tutorial).


There are a number of possibilities. The easiest possibility, which works well if you don't need to add or delete keys from your table, or change their associated values, is to construct a list of rules with the key on the left-hand side and the value on the right-hand side, and use Dispatch on it.

If you do need to change the entries in your table, you can use the DownValues of a symbol as a hash table. This will support all the operations one commonly uses with hash tables. Here's the most straightforward way of doing that:

(* Set some values in your table.*) 
In[1]:=  table[a] = foo; table[b] = bar; table[c] = baz;

(* Test whether some keys are present. *)
In[2]:=  {ValueQ[table[a]], ValueQ[table[d]]}
Out[2]:= {True, False}

(* Get a list of all keys and values, as delayed rules. *)
In[3]:=  DownValues[table]
Out[3]:= {HoldPattern[table[a]] :> foo, HoldPattern[table[b]] :> bar,
HoldPattern[table[c]] :> baz}

(* Remove a key from your table. *)
In[4]:=  Unset[table[b]]; ValueQ[table[b]]
Out[4]:= False
Szabolcs
  • 24,728
  • 9
  • 85
  • 174
Pillsy
  • 9,781
  • 1
  • 43
  • 70
8

I'd say the most similar structure you can get out of the box are sparse arrays.

infused
  • 24,000
  • 13
  • 68
  • 78
João Silva
  • 89,303
  • 29
  • 152
  • 158
  • This answer deserves several more votes. In my humble opinion, it is almost always better to use out-of-the-box structures than to construct one's own. But `Pillsy` has also given a very good answer. – Shredderroy Oct 13 '13 at 19:27
5

I agree with Pillsy, but see also this answer:

Mathematica Downvalue Lhs

It includes a handy function for getting the keys of a hash table.

Community
  • 1
  • 1
dreeves
  • 26,430
  • 45
  • 154
  • 229
4

Mathematica 10 introduces Association, <| k -> v |>,

<|a -> x, b -> y, c -> z|>
%[b]
y

Which is basically a wrapper for a list of rules: Convert a list of rules to an association:

Association[{a -> x, b -> y, c -> z}]
<|a -> x, b -> y, c -> z|>

Convert an association to a list of rules:

Normal[<|a -> x, b -> y, c -> z|>]
{a -> x, b -> y, c -> z}
Szabolcs
  • 24,728
  • 9
  • 85
  • 174
masterxilo
  • 2,503
  • 1
  • 30
  • 35
4

I've made Dictionary.m module, which contained:

DictHasKey = Function[
    {
        dict,
        key
    },
    ValueQ[dict[key]]
]

DictAddKey = Function[
    {
        dict,
        key,
        value
    },
    If[
        DictHasKey[dict,key],
        Print["Warning, Dictionary already has key " <> ToString[key]]
    ];
    dict[key] = value;
]

DictKeys = Function[
    {
        dict
    },
    res = {};
    ForEach[DownValues[dict], Function[{dictKeyDescr},
        res = Append[res, ((dictKeyDescr[[1]]) /. dict -> neverUsedSymbolWhatever)[[1, 1]]];
    ]];
    res
]

DictValues = Function[
    {
        dict
    },
    res = {};
    ForEach[DownValues[dict], Function[{dictKeyDescr},
        res = Append[res, dictKeyDescr[[2]]];
    ]];
    res
]

DictKeyValuePairs = Function[
    {
        dict
    },
    res = {};
    ForEach[DownValues[dict], Function[{dictKeyDescr},
        res = Append[res, {((dictKeyDescr[[1]]) /. dict -> neverUsedSymbolWhatever)[[1, 1]], dictKeyDescr[[2]]}];
    ]];
    res
]

ForEach = Function[
    {
        list, 
        func 
    }, 
    len = Length[list]; 
    For[i = 1, i <= len, i++, 
        func[
            list[[i]]
        ]; 
    ]; 
]
Chris Cashwell
  • 22,308
  • 13
  • 63
  • 94
Fiard
  • 41
  • 1
  • forgot: ForEach = Function[ { list, func }, len = Length[list]; For[i = 1, i <= len, i++, func[list[[i]]]; ]; ] – Fiard Nov 30 '11 at 16:40