[Python-ideas] __iter__ implies __contains__?

Devin Jeanpierre jeanpierreda at gmail.com
Sun Oct 2 18:39:59 CEST 2011


> Since iteration over elements is at the heart of containment tests, the same
> reasoning applies to __contains__.

I was with you for the old-style sequence iteration API, but you've
lost me here. I *can* imagine use-cases where "in" shouldn't work:
pretty much any iterator. Doesn't it seem strange that `x in A` should
succeed, but then `x in A` should fail?

Devin

On Sat, Oct 1, 2011 at 9:14 PM, Steven D'Aprano <steve at pearwood.info> wrote:
> Chris Rebert wrote:
>
>> <snip>
>>>
>>> the latter kicks in any time an object with no __iter__ and a __getitem__
>>> is tentatively iterated, I've made that error a few times with
>>> insufficiently defined dict-like objects finding themselves (rightly
>>> or wrongly) being iterated.
>>
>> Requiring the explicit marking of a class as a sequence by inheriting
>> from the Sequence ABC in order to get such default behavior "for free"
>> seems quite reasonable. And having containment defined by default on
>> potentially-infinite iterators seems unwise. +1 on the suggested
>> removals.
>
> These changes don't sound even close to reasonable to me. It seems to me
> that the OP is making a distinction that doesn't exist.
>
> If you can write this:
>
> x = collection[0]; do_something_with(x)
> x = collection[1]; do_something_with(x)
> x = collection[2]; do_something_with(x)
> # ... etc.
>
> then you can write it in a loop by hand:
>
> i = -1
> try:
>    while True:
>        i += 1
>        x = collection[i]
>        do_something_with(x)
> except IndexError:
>    pass
>
>
> But that's just a for-loop in disguise. The for-loop protocol goes all the
> way back to Python 1.5 and surely even older. You should, and can, be able
> to write this:
>
> for x in collection:
>    do_something_with(x)
>
>
> Requiring collection to explicitly inherit from a Sequence ABC breaks duck
> typing and is anti-Pythonic.
>
> I can't comprehend a use-case where manually extracting collection[i] for
> sequential values of i should succeed, but doing it in a for-loop should
> fail. But if you have such a use-case, feel free to define __iter__ to raise
> an exception.
>
> Since iteration over elements is at the heart of containment tests, the same
> reasoning applies to __contains__.
>
>
> --
> Steven
> _______________________________________________
> Python-ideas mailing list
> Python-ideas at python.org
> http://mail.python.org/mailman/listinfo/python-ideas
>



More information about the Python-ideas mailing list