# Re: Non-list ranges

Guido.van.Rossum@cwi.nl
Tue, 26 Oct 1993 16:16:07 +0100

> I have been follwing the thread on Non-list ranges with some
> interest and would like to mention, as a little diversion, how our
> in house language (Bacis2) does it.
> Bacis has the concept of iterator functions that "yield" values to a loop.
[...explanation deleted...]
> While this type of functionality can be achieved by writing a
> function to return a list, an iterator function does it without
> allocating space for a, potentialy very long, list.
>
> Could something like this be done in Python?

Interesting point! You can more or less do this with a class. Here
is a simple example; it yields the first n elements of the Fibonacci
sequence (1, 1, 2, 3, 5, 8, 13, ...):

class Fib:

# constructor -- argument is length of sequence
def __init__(self, n):
self.size = n
self.reset()

def reset(self):
self.last_index = 0
self.a = self.b = 1

# return len(self)
def __len__(self):
return self.size

# return self[i]
def __getitem__(self, i):
if i < self.last_index:
self.reset()
while i > self.last_index:
self.last_index = self.last_index + 1
self.a, self.b = self.b, self.a + self.b
return self.a

This example tries to behave like a real sequence -- only it is faster
when you ask for the items in their natural sequence, hence the
reset() method. For iterators that will *only* be used in a for loop,
__getitem__ could raise an expression when an item is asked for out of
sequence.

The catch is that you need to know how many values a particular
iterator instance will yield, so you can't use it to simulate an
infinite or indefinite sequence.

If iterators become popular in Python, it might be possible to
redefine the 'for' semantics and extend the interface to sequences to
allow for loops over (pseudo-)sequences of indefinite length. But I
don't know how much use there is for this, since it is generally just
as easy to use a while loop for a loop over an indefinite sequence...

--Guido van Rossum, CWI, Amsterdam <Guido.van.Rossum@cwi.nl>