[ZODB-Dev] ExtensionClass/Persistent and __cmp__ is tricky
Christian Reis
kiko at async.com.br
Sat Jun 28 00:57:24 EDT 2003
So I read the docs on BTrees and `Total Ordering' at
http://www.zope.org/Wikis/ZODB/guide/node6.html again. One of the key
points here (as Tim pointed out) is that __cmp__ has to be carefully
designed:
If you want to use class instances as keys, and there's any possibility
that the structure may be stored in a database, it's crucial that the
class define a __cmp__() method, and that the method is carefully
implemented.
I'm fine with this, so I started some verification of the __cmp__ method
on IndexedObject, our Persistent-derived class. The first, basic, test I
did, however, bothers me because it seems to echo something similar to
what Greg Ward suggested back in
http://mail.zope.org/pipermail/zope-dev/2000-May/004420.html -- that
cmp() is not completely compatible with ExtensionClass. Here's my
(short) example:
>>> from ZODB import Persistent
>>> class Foo(Persistent):
... def __cmp__(self, other):
... print "Hi there"
... return cmp(self, other)
...
>>>
>>> f = Foo()
>>> f < 1
Hi there [ repeated 21 times ]
>>> f > 1
Hi there [ repeated 21 times ]
>>> 1 < f
0
>>> 1 > f
1
This goes against what I understand of the cmp() protocol. The PSL docs
say:
__cmp__(self, other)
Called by comparison operations if rich comparison (see above) is
not defined. Should return a negative integer if self < other,
zero if self == other, a positive integer if self > other. If no
__cmp__() operation is defined, class instances are compared by
object identity (``address''). (Note: the restriction that
exceptions are not propagated by __cmp__() has been removed in
Python 1.5.)
Am I understanding this correctly? It seems you can't compare
ExtensionClass with basic types; in Python 2.1.3 at least it appears to
me that try_3way_compare doesn't want to call tp_compare on the second
instance because it's not a PyInstance.
PS: The interesting part is that it seems that comparing lists *does*
work:
>>> [] > f
Hi there [ repeated 21 times ]
0
Which means I'm almost safe with using PersistentList, at any rate
(which uses its List comparison).
PPS: Anybody know why 21 times?
Take care,
--
Christian Reis, Senior Engineer, Async Open Source, Brazil.
http://async.com.br/~kiko/ | [+55 16] 261 2331 | NMFL
More information about the ZODB-Dev
mailing list