Pairwise circular Python 'for' loop

Is there a nice Pythonic way to loop over a list, retuning a pair of elements? The last element should be paired with the first.

So for instance, if I have the list [1, 2, 3], I would like to get the following pairs:

  • 1 - 2
  • 2 - 3
  • 3 - 1

Solution 1:

A Pythonic way to access a list pairwise is: zip(L, L[1:]). To connect the last item to the first one:

>>> L = [1, 2, 3]
>>> zip(L, L[1:] + L[:1])
[(1, 2), (2, 3), (3, 1)]

Solution 2:

I would use a deque with zip to achieve this.

>>> from collections import deque
>>>
>>> l = [1,2,3]
>>> d = deque(l)
>>> d.rotate(-1)
>>> zip(l, d)
[(1, 2), (2, 3), (3, 1)]

Solution 3:

I'd use a slight modification to the pairwise recipe from the itertools documentation:

def pairwise_circle(iterable):
    "s -> (s0,s1), (s1,s2), (s2, s3), ... (s<last>,s0)"
    a, b = itertools.tee(iterable)
    first_value = next(b, None)
    return itertools.zip_longest(a, b,fillvalue=first_value)

This will simply keep a reference to the first value and when the second iterator is exhausted, zip_longest will fill the last place with the first value.

(Also note that it works with iterators like generators as well as iterables like lists/tuples.)

Note that @Barry's solution is very similar to this but a bit easier to understand in my opinion and easier to extend beyond one element.