|
19 | 19 | """
|
20 | 20 |
|
21 | 21 | from collections import Sequence, Iterator
|
| 22 | +from itertools import islice |
22 | 23 |
|
23 | 24 |
|
24 | 25 | class newrange(Sequence):
|
@@ -136,35 +137,27 @@ def __getitem_slice(self, slce):
|
136 | 137 | def __iter__(self):
|
137 | 138 | """Return an iterator which enumerates the elements of the
|
138 | 139 | sequence this range represents."""
|
139 |
| - return rangeiterator(self) |
| 140 | + return range_iterator(self) |
140 | 141 |
|
141 | 142 |
|
142 |
| -class rangeiterator(Iterator): |
| 143 | +class range_iterator(Iterator): |
143 | 144 | """An iterator for a :class:`range`.
|
144 | 145 | """
|
145 |
| - |
146 |
| - def __init__(self, rangeobj): |
147 |
| - self._range = rangeobj |
148 |
| - |
149 |
| - # Intialize the "last outputted value" to the value |
150 |
| - # just before the first value; this simplifies next() |
151 |
| - self._last = self._range._start - self._range._step |
152 |
| - self._count = 0 |
| 146 | + def __init__(self, range_): |
| 147 | + self._stepper = islice(_count(range_.start, range_.step), len(range_)) |
153 | 148 |
|
154 | 149 | def __iter__(self):
|
155 |
| - """An iterator is already an iterator, so return ``self``. |
156 |
| - """ |
157 | 150 | return self
|
158 | 151 |
|
159 | 152 | def next(self):
|
160 |
| - """Return the next element in the sequence represented |
161 |
| - by the range we are iterating, or raise StopIteration |
162 |
| - if we have passed the end of the sequence.""" |
163 |
| - self._last += self._range._step |
164 |
| - self._count += 1 |
165 |
| - if self._count > self._range._len: |
166 |
| - raise StopIteration() |
167 |
| - return self._last |
| 153 | + return next(self._stepper) |
| 154 | + |
| 155 | + |
| 156 | +# itertools.count in Py 2.6 doesn't accept a step parameter |
| 157 | +def _count(start=0, step=1): |
| 158 | + while True: |
| 159 | + yield start |
| 160 | + start += step |
168 | 161 |
|
169 | 162 |
|
170 | 163 | __all__ = ['newrange']
|
0 commit comments