Skip to content

Instantly share code, notes, and snippets.

@sachinlala
Last active January 15, 2018 08:25
Show Gist options
  • Save sachinlala/cf54133759a1a2732c544c5f7e404b1e to your computer and use it in GitHub Desktop.
Save sachinlala/cf54133759a1a2732c544c5f7e404b1e to your computer and use it in GitHub Desktop.
Rotate a Linked List clockwise or anti-clockwise, every 'k' nodes
/**
* <u>Requirement</u>: rotate w/in O(n) time and O(1) space.
*/
public class LinkedListRotation<T extends Comparable> {
public ListNode<T> rotateListLeft(ListNode<T> head, int k) {
return rotate(head, k, false);
}
public ListNode<T> rotateListRight(ListNode<T> head, int k) {
return rotate(head, k, true);
}
/**
* <br><u>Approach</u>:
* <br>0. If (k%size or k) == 0 => no/full rotation.
* <br>1. Track 2 pointers, one for originalTail and second for newTail.
* <br>2. Join originalTail with originalHead.
* <br>3. newTail : right=(n-k) | left=(k)
* <br>4. newHead = newTail.next, newTail.next = null.
* <br>5. Handle k>size i.e. k = k%size.
*/
public ListNode<T> rotate(ListNode<T> head, int k, boolean clockwise) {
if (head == null || head.next == null || k == 0) return head;
int size=1, lowerBound=1, upperBound;
ListNode<T> tail=head, newTail=head;
while (tail.next != null) {
size++;
tail = tail.next;
}
k %= size;
if (k == 0) return head;
tail.next = head;
if (clockwise) { // newTail = (n-k)
upperBound = size-k;
} else { // newTail = k
upperBound = k;
}
for (int i=lowerBound; i<upperBound; i++) {
newTail = newTail.next;
}
head = newTail.next;
newTail.next = null;
return head;
}
}
class ListNode<T extends Comparable> {
T data;
ListNode<T> next;
ListNode(T _data) {
data = _data;
next = null;
}
}
@sachinlala
Copy link
Author

Note the new HEAD & TAIL expected after the rotation:

Node CCW CW
HEAD (k+1) (n-k+1)
TAIL (k) (n-k)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment