Reputation: 275
I need to cycle through a list for starting position between 1-4
using itertools
I am able to cycle through the list
positions = itertools.cycle([1,2,3,4])
next(positions)
This does return the next position, but what if the next time I need to start at 3? How can I set the start position?
I need the start position to change often, I cant just change the list to start at 3.
Upvotes: 11
Views: 4284
Reputation: 476709
You can use itertools.islice
for that:
from itertools import cycle
from itertools import islice
positions3 = islice(cycle([1,2,3,4]),2,None)
this will result in a generator that emits 3,4,1,2,3,4,1,2,3,4,...
In case the start position k
is large (compared to the length of the original list), it can pay off to perform a modulo first:
from itertools import cycle
from itertools import islice
source_list = [1,2,3,4]
k = 10000000 # offset index
positions_k = islice(cycle(source_list),k%len(source_list),None)
This will generate an equivalent result, but islice
will not drop the first 10M elements.
Upvotes: 4
Reputation: 1122232
You can't set a starting position; it'll always start where the given sequence starts.
You can move the cycle along a few steps before you use it for whatever you need it for. Use itertools.islice()
to skip some items:
from itertools import islice
starting_at_three = islice(positions, 2, None)
You pass in the iterable, then a start and stop value; None
here means that the islice()
iterator continues forever or until the underlying positions
iterator is exhausted.
Demo:
>>> from itertools import islice, cycle
>>> positions = cycle([1, 2, 3, 4])
>>> starting_at_three = islice(positions, 2, None)
>>> next(starting_at_three)
3
>>> next(starting_at_three)
4
>>> next(starting_at_three)
1
The other option is to pass in a different sequence; you could pass in [3, 4, 1, 2]
for example.
Upvotes: 13
Reputation: 107297
Use slices of the original list:
In [15]: def custom_slice(lst, start):
....: return cycle(lst[start:] + lst[:start + 1])
Demo:
In [16]: positions = custom_slice(lst, 2)
In [17]: next(positions)
Out[17]: 3
In [18]: next(positions)
Out[18]: 4
In [19]: next(positions)
Out[19]: 1
In [20]: next(positions)
Out[20]: 2
Upvotes: 0