Skip to content
← All posts

Shuffle the Array: Interleaving Two Halves in Place

5 min read
leetcodeproblemeasyarrays

LeetCode 1470. Shuffle the Array gives you an array of 2n elements in the form [x1, x2, ..., xn, y1, y2, ..., yn] and asks you to return the array in the form [x1, y1, x2, y2, ..., xn, yn]. In other words, interleave the first half and the second half like a perfect riffle shuffle with a deck of cards.

For example, given nums = [2, 5, 1, 3, 4, 7] and n = 3, the output is [2, 3, 5, 4, 1, 7]. The first half [2, 5, 1] and the second half [3, 4, 7] get zipped together into alternating positions.

Input2x15x21x33y14y27y3first halfsecond halfOutput235417
Input [2, 5, 1, 3, 4, 7] with n = 3. Elements from the first half (x) and second half (y) interleave into the output.

Why this problem matters

Shuffle the Array is rated easy, and the code is short. But it teaches a pattern that comes up more often than you might expect: splitting an array into two logical halves and recombining them according to some rule. Variations of this idea appear in merge sort, partition-based algorithms, and problems that ask you to rearrange elements by index parity.

It is also a good warm-up for understanding how index arithmetic translates to array positions. The relationship result[2*i] = nums[i] and result[2*i + 1] = nums[i + n] is simple, but getting comfortable mapping between source and destination indices is a skill that pays off in harder problems.

The key insight

You do not need to think of this as "shuffling" at all. The problem is really just a zip operation. For each index i from 0 to n - 1, you want to place nums[i] and nums[i + n] next to each other in the result. That is one loop, two reads per iteration, and you are done.

The key observation is that element i from the first half goes to position 2 * i in the output, and element i + n from the second half goes to position 2 * i + 1. Once you see that mapping, the code writes itself.

The solution

def shuffle(nums: list[int], n: int) -> list[int]:
    result = []
    for i in range(n):
        result.append(nums[i])
        result.append(nums[i + n])
    return result

The loop iterates n times. On each iteration, it grabs the next element from the first half (nums[i]) and the corresponding element from the second half (nums[i + n]), appending both to the result. After the loop, the result array contains all 2n elements interleaved in the correct order.

You can also write this as a list comprehension: [v for i in range(n) for v in (nums[i], nums[i + n])]. It does the same thing in one line. Both are valid, but the explicit loop is easier to explain in an interview.

Visual walkthrough

Let's trace through nums = [2, 5, 1, 3, 4, 7] with n = 3 to see exactly how the elements get paired and placed.

Step 1: Identify the two halves

2x15x21x33y14y27y3

The first n elements are x values. The second n elements are y values.

Step 2: Pair up x[i] with y[i]

2x13y15x24y21x37y3

Each x element pairs with the y element at the same offset: (x1,y1), (x2,y2), (x3,y3).

Step 3: Build the result by iterating i from 0 to n-1

235417012345

For each i, append nums[i] then nums[i + n] to the result array.

Result: [2, 3, 5, 4, 1, 7]

203152431475

Every even index holds an x value, every odd index holds a y value. Done in one pass.

Each iteration of the loop handles one pair. After three iterations, all six elements are in the result array in the correct interleaved order.

Complexity analysis

ApproachTimeSpace
Single pass with new arrayO(n)O(n)

Time: the loop runs n times, and each iteration does O(1) work (two appends). Total: O(n).

Space: we create a new result array of size 2n, so the extra space is O(n). Since the problem asks you to return a new array, this is the expected approach.

The building blocks

This problem breaks down into two reusable pieces that show up across many array problems:

1. Index mapping between source and destination

The core idea is computing where each element should go. Here, nums[i] maps to result[2*i] and nums[i + n] maps to result[2*i + 1]. This type of index arithmetic appears whenever you need to rearrange elements according to a formula rather than a comparison.

for i in range(n):
    result[2 * i] = nums[i]
    result[2 * i + 1] = nums[i + n]

2. Splitting an array into logical halves

Treating a single array as two separate halves based on an offset is a pattern you will see in merge sort, partition, and many divide-and-conquer problems. The first half is nums[0:n] and the second half is nums[n:2n]. No slicing is needed. You just use i and i + n as your two read pointers.

for i in range(n):
    first_half_element = nums[i]
    second_half_element = nums[i + n]

3. Zipping two sequences together

The interleaving pattern itself (take one from A, take one from B, repeat) is the same operation as Python's zip. Recognizing this lets you use built-in tools when appropriate.

result = []
for a, b in zip(nums[:n], nums[n:]):
    result.extend([a, b])

Edge cases

  • n = 1: the array has exactly two elements [x1, y1]. The output is [x1, y1], unchanged. The loop runs once and appends both elements.
  • All elements are the same: if nums = [5, 5, 5, 5] with n = 2, the output is [5, 5, 5, 5]. The algorithm does not depend on values being distinct.
  • Large n: with up to 500 elements (the constraint says n can be up to 500, so the array has up to 1000 elements), the O(n) solution handles it instantly.
  • Elements at the boundary: nums[n-1] is the last element of the first half and nums[n] is the first element of the second half. They end up at positions 2*(n-1) and 2*0 + 1 respectively, which is correct.

From understanding to recall

The code for this problem is about five lines. The logic is not complicated. But the index mapping (i to 2*i, i + n to 2*i + 1) is the kind of detail that fades if you do not practice it. Two weeks from now, when you see a problem that asks you to interleave or rearrange elements by position, you want the pattern to fire immediately.

That is what spaced repetition is for. You drill the index-mapping brick and the zip-two-halves brick as individual building blocks, typing them from scratch at increasing intervals. After a few cycles, the code is in your fingers, not just your head. CodeBricks breaks problems like this into their reusable components and schedules them so you build permanent recall.

Related posts

  • Rotate Array - Another array rearrangement problem where index arithmetic determines where each element ends up
  • Product of Array Except Self - An array problem that uses a two-pass technique to compute results based on surrounding elements
  • Contains Duplicate - A foundational easy array problem that introduces the single-pass pattern with a hash set