You are given the head
of a singly linked list. Your task is to rotate the list to the right by k
places, where k
is a non-negative integer. The rotation should be performed in-place.
For example:
1 -> 2 -> 3 -> 4 -> 5
and k = 2
, the rotated list should be 4 -> 5 -> 1 -> 2 -> 3
.0 -> 1 -> 2
and k = 4
, the rotated list should be 2 -> 0 -> 1
.null
.Constraints:
[0, 500]
.-100 <= Node.val <= 100
0 <= k <= 2 * 10^9
Write a function that takes the head
of the linked list and an integer k
as input and returns the head of the rotated linked list.
When you get asked this question in a real-life environment, it will often be ambiguous (especially at FAANG). Make sure to ask these questions in that case:
We need to shift a list of items by a certain amount. The brute force method involves repeatedly moving items from one end of the list to the other, one position at a time, until we've shifted enough.
Here's how the algorithm would work step-by-step:
def rotate_list_brute_force(input_list, rotation_amount):
list_length = len(input_list)
# Normalize rotation amount to avoid unnecessary rotations
effective_rotation = rotation_amount % list_length
for _ in range(effective_rotation):
# Store the last element before rotation
last_element = input_list[-1]
# Insert the last element at the beginning
input_list.insert(0, last_element)
# Remove the duplicated last element
del input_list[-1]
return input_list
The problem asks us to shift the elements in a chain of items. The clever trick is to realize you don't need to move items one by one. Instead, think of cutting and rearranging the chain.
Here's how the algorithm would work step-by-step:
class ListNode:
def __init__(self, value=0, next_node=None):
self.value = value
self.next_node = next_node
def rotate_right(head, rotation_amount):
if not head:
return None
list_length = 1
tail_node = head
while tail_node.next_node:
tail_node = tail_node.next_node
list_length += 1
# Effective rotation amount handles rotations > list length.
effective_rotation = rotation_amount % list_length
if effective_rotation == 0:
return head
# Find the node before the new head.
new_tail_position = list_length - effective_rotation
current_node = head
for _ in range(new_tail_position - 1):
current_node = current_node.next_node
# Break the list into two parts.
new_head = current_node.next_node
current_node.next_node = None
# Connect the tail to the original head.
tail_node.next_node = head
return new_head
Case | How to Handle |
---|---|
head is null | Return null immediately to avoid NullPointerException. |
Empty list (head is null) and k is 0 | Return null as there's nothing to rotate. |
Single node list | Return the head itself as rotating doesn't change anything. |
k is 0 | Return the original head without any changes. |
k is a large value, potentially larger than the length of the list | Calculate k % length to get the effective rotation value. |
k is equal to the length of the linked list | Return the original head as rotating by the length has no effect. |
List with many nodes (performance concerns) | Ensure solution avoids unnecessary iterations by calculating effective k and correctly relinking nodes. |
List with only two nodes, and k = 1 | Handle the swapping of head and tail correctly. |