[Python-ideas] Break the dominance of boolean values in boolean context

Guido van Rossum guido at python.org
Tue Sep 13 19:56:23 CEST 2011


On Mon, Sep 12, 2011 at 9:51 PM, Nick Coghlan <ncoghlan at gmail.com> wrote:
> On Tue, Sep 13, 2011 at 2:09 PM, Guido van Rossum <guido at python.org> wrote:
>> On Mon, Sep 12, 2011 at 8:39 PM, Nick Coghlan <ncoghlan at gmail.com> wrote:
>>> On Tue, Sep 13, 2011 at 11:40 AM, Devin Jeanpierre
>>> <jeanpierreda at gmail.com> wrote:
>>>> Can we not allow things like `a < b` to return non-boolean values,
>>>> without altering the behaviour of existing Python types?
>>>
>>> We already do. As far as I am aware, the only holdouts are:
>>>
>>> x in a (coerces to bool)
>>> not a (coerces to bool)
>>> a and b (doesn't coerce as such, but roughly equivalent to "a if not a else b")
>>> a or b (doesn't coerce as such, but roughly equivalent to "a if a else b")
>>>
>>> The first case can already be overridden (via __contains__)
>>
>> But does the C code wrapping it preserve the non-bool value? (IIRC
>> originally many of these were constrained by the C implementation more
>> than by any philosophical desire to keep bool pure.)
>>
>>> and I
>>> don't believe there's any specific reason for retaining the coercion
>>> to bool (aside from nobody writing and championing a patch that
>>> eliminates the restriction).
>>
>> Oh I see, you are saying that there is no need *in principle*. Agreed
>> for __contains__. (BTW there is also a need for the reverse operator.
>> Maybe it could be called __in__?)
>
> The two issues seem somewhat orthogonal to me, but yes, the general
> idea would be to make 'in' behave more like a rich comparison operator
> rather than an explicitly boolean operation as it does now.
>
> It occurs to me that adding __in__ could also address a slight
> performance oddity with 3.2 range objects: the __contains__ check in
> 3.2 has an O(1) fast path for containment checks on actual Python
> integers, but falls back to the O(n) sequential search for objects
> that only implement __index__(). If __in__() was available, such
> objects could conceivably map containment tests to checks against the
> corresponding real Python integer (although doing that carelessly
> would do weird things to other containers, such as identity-keyed
> dictionaries. That would be a quality of implementation issue on
> __in__ methods, though).

I guess I might understand this paragraph if you pointed me to the code. :-(

>> But I'm not sure I want to pay the price for this flexibility
>> everywhere where those operators are used in their traditional
>> meanings. Admittedly I haven't read PEP 335 thoroughly.
>
> I think that's a pretty good explanation for why PEP 335 hasn't been
> pushed too hard - there's a lot of value in having not/and/or behave
> more like control flow structures rather than ordinary operations. PEP
> 335 does show that it's theoretically possible to make them behave
> more like operators, but that doesn't make it a good idea.
>
> To be honest, I don't think anyone would cry too much if you decided
> to explicitly reject it on the basis of continuing to allow control
> flow optimisations for code involving not/and/or. While CPython
> doesn't do it, I believe there *are* control flow transformations that
> the current semantics permit that PEP 335 would disallow, such as
> automatically applying De Morgan's Law (I don't actually have a use
> case for doing that, I'm just mentioning it as a consequence of the
> semantics change proposed by the PEP).

I think I just mentioned one (turning 'if not' into a jump). Anyway,
I'm glad to reject the PEP for the reason that I like the status quo
just fine. (But relaxing __contains__ and adding __in__ as its reverse
have my blessing.) Also, after reading the PEP from beginning to end,
and downloading and skimming the patch (but failing to actually
compile a patched version of Python 2.3), I think the offered API is
too complicated to be of much use. Certainly the NumPy folks have
repeatedly claimed that they are fine with the status quo.

-- 
--Guido van Rossum (python.org/~guido)



More information about the Python-ideas mailing list