For loop range and interval, how to include last step

Viewed 7269

What is the best way to make a for loop such that

 for i in range(0,99,20)

iterates over i = 0 20 40 60 80 99?

rather than just i = 0 20 40 60 80?

Right now I have an if statement to check if modulo != 0 and tacks on an extra iteration if true.

3 Answers

This is impossible to do with Python's range. But this can be accomplished by creating your own generator function.

def myRange(start,end,step):
    i = start
    while i < end:
        yield i
        i += step
    yield end


for i in myRange(0,99,20):
    print(i)

Output:

0
20
40
60
80
99

First of all, it usually does not makes much sense to include the end condition, the idea of a range is to perform hops until the end value is reached.

Nevertheless, you can for instance use itertools.chain for that:

from itertools import chain

for i in chain(range(0,99,20), [99]):
    # ...
    pass

chain concatenates iterables together. So after the range(..) is exhausted, it will iterate over the next iterable, and so on.

The above approach is not very elegant: it requires some knowledge about how chain works. We can however encapsulate that logic:

def range_with_end(start, stop, step):
    return chain(range(start, stop, step), (stop,))

Or, more simply, with a generator:

def hop(start, stop, step):
    for i in range(start, stop, step):
        yield i
    yield stop

print(list(hop(0, 99, 20)))

[0, 20, 40, 60, 80, 99]
Related