AlgoMaster Logo

Reorder List

mediumFrequencyUpdated September 21, 2026

Understanding the Problem

We need to rearrange a singly linked list so that nodes alternate between the front and the back. Take the first node, then the last node, then the second node, then the second-to-last node, and so on. The difficulty is that this is a singly linked list, so we cannot traverse backward to reach those "back" nodes cheaply.

The reordered list is the first half of the original interleaved with its second half reversed. For [1, 2, 3, 4, 5], that means interleaving the first half [1, 2, 3] with the reversed second half [5, 4] to get 1 -> 5 -> 2 -> 4 -> 3. Every approach below relies on this structure. They differ only in how they reach the back nodes: by copying references into an array, or by reversing the second half in place.

Key Constraints:

  • Up to 5 * 10^4 nodes. An O(n^2) approach, such as repeatedly scanning to the tail to find the last unplaced node, would run up to 2.5 billion operations and time out. An O(n) solution is required.
  • The list is singly linked, so we cannot walk backward. Any approach that needs the back nodes must either copy node references into a random-access structure or reverse part of the list in place.
  • Values are fixed (1 <= Node.val <= 1000) and must not be modified. We rearrange the nodes themselves, never their values, so the value range does not affect the approach.

Approach 1: Using an Array

Intuition

The difficulty with a singly linked list is the lack of backward movement. Storing every node reference in an array removes that restriction: an array gives O(1) access to any position, including the last. With all nodes in an array, two pointers, one at the front and one at the back, can rewire the next connections directly in the required interleaved order.

This spends O(n) extra space to avoid any pointer reversal. It is the more direct of the two approaches and a useful baseline before the in-place version.

Algorithm

  1. Traverse the linked list and store each node reference in an array.
  2. Initialize two pointers: left = 0 and right = n - 1 (where n is the number of nodes).
  3. While left < right:
    • Set nodes[left].next = nodes[right] (connect front node to back node).
    • Advance left by 1.
    • If left == right, break (we've met in the middle).
    • Set nodes[right].next = nodes[left] (connect back node to the next front node).
    • Decrement right by 1.
  4. Set the last node's next to null to terminate the list.

Visualization and Code

Loading animation...

The array stores every node, so this uses O(n) extra space. The next approach reaches the back nodes by reversing the second half in place, which removes the array and drops the space to O(1).

Approach 2: Find Middle + Reverse + Merge

Intuition

The reordered list is the first half interleaved with the reversed second half, and all three pieces can be done in place with constant extra space:

  1. Find the middle of the list, which splits it into two halves.
  2. Reverse the second half.
  3. Merge the two halves by alternating nodes.

Finding the middle uses two pointers at different speeds: slow moves one node per step, fast moves two. When fast can no longer advance two nodes, slow sits at the end of the first half. We then reverse everything after slow and alternate nodes from the two halves.

Algorithm

  1. Use slow and fast pointers to find the middle of the list. After this, slow points to the end of the first half.
  2. Reverse the second half of the list starting from slow.next. Use the standard iterative reversal (prev/curr/next pointers).
  3. Disconnect the first half from the second half by setting slow.next = null.
  4. Merge the two halves: take one node from the first half, then one from the second half, alternating until both lists are exhausted.

Visualization and Code

Loading animation...