On Wed, 5 Aug 2015 at 15:26 Paul Moore <p.f.moore@gmail.com> wrote:
On 5 August 2015 at 15:15, Ed Kellett <edk141@gmail.com> wrote:
> That said, there are solutions, and as far as I can tell it's the only
> problem that's been raised in the thread.

Are there solutions? No-one has come up with one, to my knowledge.

You need to cover

1. All of the many internal iterator types in Python:

>>> type(iter([]))
<class 'list_iterator'>
>>> type({}.keys())
<class 'dict_keys'>
>>> type({}.values())
<class 'dict_values'>
>>> type({}.items())
<class 'dict_items'>
>>> type(iter((1,2)))
<class 'tuple_iterator'>

Please don't dismiss this as "just a matter of coding". It's also
necessary to remember to do this for every new custom iterator type.

2. Generator functions and expressions:

>>> def f():
...   yield 1
...   yield 2
...
>>> type(f())
<class 'generator'>
>>> type((i for i in [1,2,3]))
<class 'generator'>

"just another internal type", yeah I know...

3. User defined iterators:

>>> class I:
...   def __next__(self):
...     return 1
...
>>> type(I())
<class '__main__.I'>

It is *not* acceptable to ask all users to retro-fit an "__add__
method to all their custom iterator types. Even if it were, this would
fail for types which are their own iterator and have a custom __add__
of their own.

4. Iterators defined in 3rd party modules, which is similar to
user-defined iterators, but with a much wider user base, and much more
stringent compatibility issues to consider.

Hand-waving away the real issues here is not an option.

Yes, this is why I replied to say they were real issues.

Well, one solution would be to have + special-case iterators, and try an iterator-add if there would be a TypeError otherwise. I think this is horrible; I'm just mentioning it for completeness.

The other solution would be an Iterator ABC that you'd inherit as a mixin, and recognizes anything as a subclass that implements the current iterator protocol + __add__.

Python could do this for 1 and 2. 3 and 4 would be more difficult and ultimately require the author of the class to either inherit Iterator or write an __add__, but this might be eased a bit by having iter() wrap iterators that aren't instances of Iterator.

> Even if it were, this would
> fail for types which are their own iterator and have a custom __add__
> of their own.

Yes. I don't think there's a solution to this part—as I said before, I think the root of the problem is Python's lack of user-defined operators.

edk