[Python-ideas] Consider making enumerate a sequence if its argument is a sequence
abarnert at yahoo.com
Wed Sep 30 20:26:03 CEST 2015
On Sep 30, 2015, at 11:11, M.-A. Lemburg <mal at egenix.com> wrote:
>> On 30.09.2015 19:19, Neil Girdhar wrote:
>> I guess, I'm just asking for enumerate to go through the same change that
>> range went through. Why wasn't it a problem for range?
> range() returns a list in Python 2 and a generator in Python 3.
No it doesn't. It returns a (lazy) sequence. Not a generator, or any other kind of iterator.
I don't know why so many people seem to believe it returns a generator. (And, when you point out what it returns, most of them say, "Why was that changed from 2.x xrange, which returned a generator?" but xrange never returned a generator either--it returned a lazy almost-a-sequence from the start.)
There's no conceptual reason that Python couldn't have more lazy sequences, and tools to build your own lazy sequences more easily.
However, things do get messy once you get into the details. For example, zip can return a lazy sequence if given only sequences, but what if it's given iterators, or other iterables that aren't sequences; filter can return something that's sort of like a sequence in that it can be repeatedly iterated but it can't be randomly-accessed. You really need a broader concept that integrates iteration and indexing, as in the C++ standard library. Swift provides the perfect example of how you could do something like that without losing the natural features of Python indexing and iteration. But it turns out to be complicated to explain, and to work with, and you end up writing multiple implementations for each iterable-processing function. I don't think the benefit is worth the cost.
Another alternative is just to wrap any iterable in a caching LazyList type. This runs into complications because there are different choices that make sense for different uses (obviously you have to handle negative indexing, and obviously you have to handle infinite lists, so... Oops!), so it makes more sense to leave that up to the application to supply whatever lazy list type it needs and use it explicitly.
More information about the Python-ideas