[Python-3000] [Python-Dev] misbehaving __contains__
Guido van Rossum
guido at python.org
Tue Jan 22 22:36:33 CET 2008
I can't promise a patch is accepted before I see it. :-)
But the idea is sound, so don't worry about it being rejected on the
basis of being an undesirable feature.
--Guido
On Jan 22, 2008 12:36 PM, tomer filiba <tomerfiliba at gmail.com> wrote:
> i can work on a patch, but before i start, i want to make sure it's
> accepted. the change will require sq_contains to return a PyObject,
> as well as some minor tweaks to cmp_outcome().
>
>
> -tomer
>
> ---------- Forwarded message ----------
> From: Guido van Rossum <guido at python.org>
> Date: Jan 22, 2008 9:55 PM
> Subject: Re: [Python-Dev] misbehaving __contains__
> To: tomer filiba <tomerfiliba at gmail.com>
> Cc: python-dev at python.org
>
>
> The issue is that the sq_contains slot is defined as returning an int,
> while the tp_richcompare slot is defined as returning a PyObject *.
>
> Your first opportunity for changing this will be Py3k. Please submit a patch!
>
>
>
> On Jan 22, 2008 11:26 AM, tomer filiba <tomerfiliba at gmail.com> wrote:
> > i'm using python to create expression objects, for more intuitive
> > usage as
> > predicates, for instance:
> > x = (Arg(0) > 17) & (Arg(1).foo == "bar")
> > instead of
> > x = And(Gt(Arg(0), 17), Eq(GetAttr(Arg(1), "foo"), "bar"))
> >
> > so now i can use x.eval(18, "spam") and get the result of the
> > expression.
> >
> > i'm doing it by overriding all the operators to return expression
> > objects, instead of evaluating the result immediately. it works
> > fine, but i encountered a problem with making
> > __contains__ behave so.
> >
> > it turns out __contains__ coerces the return value into a bool.
> > this might seem logical at first, but is not consistent with
> > the rest of the language.
> >
> > consider the following code:
> >
> > >>> class Foo(object):
> > ... def __contains__(self, key):
> > ... return 17
> > ... def __eq__(self, other):
> > ... return 19
> > ...
> > >>>
> > >>> f=Foo()
> > >>> f == 8
> > 19
> > >>> 8 in f
> > True
> >
> > as you can see, __eq__ does not coerces the result to bool, so why
> > should __contains__ do that?
> >
> > i've looked at PySequence_Contains in objects/abstract.c, but i can't
> > quite understand where the coercion is made. is because the
> > function is typed as int? if so, i believe it should either be
> > changed to PyObject, or have cmp_outcome (in ceval.c) not use this
> > API directly, and rather return the result, as it is returned
> > from __contains__.
> >
> > i see no reason it should behave differently than __eq__ and the rest
> > of comparison operators.
> >
> >
> > -tomer
>
> --
>
> --Guido van Rossum (home page: http://www.python.org/~guido/)
>
--
--Guido van Rossum (home page: http://www.python.org/~guido/)
More information about the Python-3000
mailing list