简体   繁体   中英

itertools.repeat VS itertools.cycle

Is there any difference between itertools.repeat(n) and itertools.cycle(n) ? As it seems, they produce the same output. Is one more efficient to use in a situation where I need an infinite loop of some element?

Simply, itertools.repeat will repeat the given argument, and itertools.cycle will cycle over the given argument. Don't run this code, but for example:

from itertools import repeat, cycle

for i in repeat('abcd'): print(i)
# abcd, abcd, abcd, abcd, ...

for i in cycle('abcd'): print(i)
# a, b, c, d, a, b, c, d, ...

These are equivalent but the first is clearer and a little faster:

it = repeat(x)
it = cycle([x])

However, cycle has the option of repeating entire sequences:

it = cycle(['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday'])

And repeat has the option of setting a limit on the number of repetitions:

it = repeat(x, 5)         # Return five repetitions of x

Also, the intended use cases are different.

In particular, repeat was designed to provided a repeated argument to a mapped function:

it = imap(pow, repeat(2), range(10))

While cycle is intended for cyclic recurring behaviors. Here is a Python 3 example that returns 1/1 - 1/3 + 1/5 - 1/7 + 1/9 + ... :

it = accumulate(map(operator.truediv, cycle([1, -1]), count(1, 2)))

The latter example shows how all the parts fit together the create an "iterator algebra".

Hope you found this to be illuminating :-)

itertools.cycle() takes an iterator . You can't do, for example, itertools.cycle(5) - this will throw an error:

>>> itertools.cycle(3)
Traceback (most recent call last):
   File "<stdin>", line 1, in <module>
TypeError: 'int' object is not iterable

itertools.repeat() will repeat the same element over and over again - it is not designed to iterate through the elements of an iterator. It is very good for returning the same object over and over again.

In other words, doing itertools.repeat([1,2,3], 5) does:

>>>>[i for i in itertools.repeat([1,2,3], 5)]
[[1, 2, 3], [1, 2, 3], [1, 2, 3], [1, 2, 3], [1, 2, 3]]

while doing itertools.cycle([1,2,3]) returns an infinite list that looks like [1,2,3,1,2,3,1,2,3,...] (or it least it would if you could fit it in memory somehow).

The difference is fairly profound.

Refer to the itertools documents to know the difference.

>>> import itertools
>>> help(itertools.repeat)
Help on class repeat in module itertools:

class repeat(__builtin__.object)
 |  repeat(object [,times]) -> create an iterator which returns the object
 |  for the specified number of times.  If not specified, returns the object
 |  endlessly.
 |
...
...

>>> help(itertools.cycle)
Help on class cycle in module itertools:

class cycle(__builtin__.object)
 |  cycle(iterable) --> cycle object
 |
 |  Return elements from the iterable until it is exhausted.
 |  Then repeat the sequence indefinitely.
 |

itertools.repeat returns the same object over and over again, and itertools.cycle iterates over the same object over and over again. So:

import itertools

# Warning: infinite loop ahead
for x in itertools.repeat([1, 2, 3]):
    print(x)
    # [1, 2, 3], [1, 2, 3], ...

for x in itertools.cycle([1, 2, 3]):
    print(x)
    # 1, 2, 3, 1, 2, 3, ...

So if what you want is something that returns one object several times, use itertools.repeat ; and if it's something that loops over some different object use itertools.cycle .

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM