[Python-Dev] Why is the return value of __contains__ coerced to boolean, but that of __lt__ and the like is not?

Ben Hoyt benhoyt at gmail.com
Mon Jul 15 02:29:46 CEST 2013


Oh, just to show what I mean here with some code (same in both Python 2.x
and 3.x):

-----
from __future__ import print_function

class C(object):
    def __contains__(self, x):
        print('__contains__({0!r})'.format(x))
        return x

    def __lt__(self, x):
        print('__lt__({0!r})'.format(x))
        return x

c = C()
print(42 in c)
print(0 in c)
print(c < 42)
print(c < 0)
-----

This prints the following:

__contains__(42)
True
__contains__(0)
False
__lt__(42)
42
__lt__(0)
0

Whereas I'd kinda expect it to print:

__contains__(42)
42
__contains__(0)
0
__lt__(42)
42
__lt__(0)
0

-Ben



On Mon, Jul 15, 2013 at 12:21 PM, Ben Hoyt <benhoyt at gmail.com> wrote:

> I'm curious why the return value of __contains__ is coerced to True or
> False, whereas the return value of "normal" comparison operators like
> __lt__ and the like are not. The latter return the value directly without
> forcing it to be True or False.
>
> This makes overriding __contains__ significantly less flexible, so I'm
> wondering why it's designed or implemented that way. (I believe it's the
> cmp_outcome() function in Python/ceval.c that does this:
> http://hg.python.org/cpython/file/db9fe49069ed/Python/ceval.c#l4545)
>
> For example, the "peewee" ORM overloads __lt__ and the like so it can map
> Python expressions to SQL. But it can't do this with the "in" operator due
> to the result of "x in y" always returning True or False in Python. So it
> (ab)uses the "<<" operator to do this instead (See the peewee docs at
> http://peewee.readthedocs.org/en/latest/peewee/querying.html#column-lookups
> ).
>
> I'm sure there's a good reason for why "in" is different here, but I can't
> see why right now.
>
> -Ben
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.python.org/pipermail/python-dev/attachments/20130715/13d195a3/attachment.html>


More information about the Python-Dev mailing list