How to define a class that can act as dictionary key?

L

Lambda

Hi,

I'd like to define a class to use it as a dictionary key:

class dict_entry:
def __init__(self, term = "", doc_freq = 0):
self.term = term
self.doc_freq = doc_freq

def __cmp__(self, entry):
return isinstance(entry, dict_entry) and cmp(self.term,
entry.term)

def __str__(self):
return term + ", " + str(docid)

And later...
entry = dict_entry(term, len(index[term]))
self.index[entry] = []

When I run it, it says "TypeError: unhashable instance"

It looks like I can't use the new class object as the dictionary key.
What should I do?
 
P

Paul Rubin

Lambda said:
When I run it, it says "TypeError: unhashable instance"

It looks like I can't use the new class object as the dictionary key.
What should I do?

You have to add a __hash__ method. Untested:

def __hash__(self): return (self.term, self.doc_freq)

is probably the easiest.
 
B

Bruno Desthuilliers

Lambda a écrit :
Hi,

I'd like to define a class to use it as a dictionary key:

Others already answered (define the __hash__ method). Just one point:
the value returned by the __hash__ method should not change for the
lifetime of the object. So if you use instance attributes to compute the
hash, make sure these attributes won't change, else you may have a surprise:
.... def __init__(self, a, b):
.... self.a = a; self.b = b
.... def __hash__(self):
.... return hash((self.a, self.b))
....
>>> f = Foo("un", "deux")
>>> d = {f:"un deux"}
>>> d[f] "un deux"
>>> f.a = "zero"
>>> d[f]
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
KeyError: <__main__.Foo object at 0x9d04b2c>



HTH
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,743
Messages
2,569,478
Members
44,899
Latest member
RodneyMcAu

Latest Threads

Top