Why is dictionary.keys() a list and not a set?

Mike Meyer mwm at mired.org
Fri Nov 25 18:21:21 EST 2005


Christoph Zwerschke <cito at online.de> writes:
> Mike Meyer wrote:
>  > The mutability - or immutability - of an object is irrelevant to
>  > the question of whether or not they can be a dictionary key/set
>  > element. The critical property is that they are hashable.
>  > *Most* immutable builtin types are hashable, and no builtin
>  > mutable types are hashable, which deserves a mention.
> I think the problem we are facing is that you must distinguish between
> hashable/mutable *types* and hashable/mutable objects. You can have
> *types* like tuple which are hashable/immutable themselves, but can
> have *instances* that are mutable and not hashable, such as ([]).

I think you're trying to tweak the wrong definition. Types are
immutable if their instances are immutable. The problem is that python
defines the value of container objects to depend on their contents, so
the value of a container object can change even if the container
itself can't change. Tuples can't change - a tuple will always refer
to the objects it refers to when created. However, those objects can
change, which changes the value of the tuple without changing the
tuple. So whether or not a tuple containing a mutable object is
immutable depends on whether you define a immutable as "the object
can't change" or "the objects value can't change".

> For the built-in types I think objects are hashable if and only if
> they are immutable (not 100% sure, but can you give a
> counterexample?). That's why I got back to talk about mutability
> first. But I agree one should also explain the problem of non-built-in
> types.

If you define immutable as "the object doesn't change", then the
counterexample is the one you misspelled above: ([],). If you define
immutable as "the value of the object can't change", then I don't have
a counterexample.

> class mylist(list):
>      pass
>
> This class definitely has a __hash__ method. But instances of this
> class are not hashable.

Do you think it's really necessary to specify "has a __hash__ method
that returns a value", as opposed to just "has a __hash__ method"?

     <mike
-- 
Mike Meyer <mwm at mired.org>			http://www.mired.org/home/mwm/
Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information.



More information about the Python-list mailing list