Python list rotation

PythonListRotation

Python Problem Overview


> Possible Duplicate:
> Efficient way to shift a list in python

I'd like to rotate a Python list by an arbitrary number of items to the right or left (the latter using a negative argument).

Something like this:

>>> l = [1,2,3,4]
>>> l.rotate(0)
[1,2,3,4]
>>> l.rotate(1)
[4,1,2,3]
>>> l.rotate(-1)
[2,3,4,1]
>>> l.rotate(4)
[1,2,3,4]

How might this be done?

Python Solutions


Solution 1 - Python

def rotate(l, n):
    return l[-n:] + l[:-n]

More conventional direction:

def rotate(l, n):
    return l[n:] + l[:n]

Example:

example_list = [1, 2, 3, 4, 5]

rotate(example_list, 2)
# [3, 4, 5, 1, 2]

The arguments to rotate are a list and an integer denoting the shift. The function creates two new lists using slicing and returns the concatenatenation of these lists. The rotate function does not modify the input list.

Solution 2 - Python

If applicable, you could use collections.deque as a solution:

import collections

d = collections.deque([1,2,3,4,5])
d.rotate(3)

print d
>>> deque([3, 4, 5, 1, 2])

As a bonus, I'd expect it to be faster than in-built list.

Solution 3 - Python

The following function will rotate the list l, x spaces to the right:

def rotate(l, x):
  return l[-x:] + l[:-x]

Note that this will only return the original list if x is outside the range [-len(l), len(l)]. To make it work for all values of x, use:

def rotate(li, x):
  return li[-x % len(li):] + li[:-x % len(li)]

Solution 4 - Python

>>> l=[1,2,3,4]
>>> l[1:]+l[:1]
[2, 3, 4, 1]
>>> l=[1,2,3,4]
>>> l[2:]+l[:2]
[3, 4, 1, 2]
>>> l[-1:]+l[:-1]
[4, 1, 2, 3]

A general rotate n to the left (positive y in the call to rotate) or right (negative y) then:

def rotate(l, y=1):
   if len(l) == 0:
      return l
   y = y % len(l)    # Why? this works for negative y
   
   return l[y:] + l[:y]

If you want the direction of rotation to be the same as your example, just negate y in rotate.

def rotate(l, y=1):
   if len(l) == 0:
      return l
   y = -y % len(l)     # flip rotation direction
   
   return l[y:] + l[:y]

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionDrew NoakesView Question on Stackoverflow
Solution 1 - PythonYXDView Answer on Stackoverflow
Solution 2 - PythontomaszView Answer on Stackoverflow
Solution 3 - PythonAaron DufourView Answer on Stackoverflow
Solution 4 - Pythonthe wolfView Answer on Stackoverflow